From 53c79c5d851e0355986d6fabfc2881d309a22258 Mon Sep 17 00:00:00 2001 From: Jeffrey Han Date: Sat, 16 May 2015 21:25:19 -0400 Subject: [PATCH] Major refactoring - now using far more logical class names. - Renamed "OsuFile" to "Beatmap". All related variables and methods with "osu" have also been renamed to "beatmap" (or variants of each). - Renamed "OsuGroupNode" to "BeatmapSetNode". Avoids confusion since groups are identified by a "set ID", not a "group ID". - Renamed "OsuGroupList" to "BeatmapSetList", for the same reason as above. - Renamed "OsuDB" to "BeatmapDB", for the same reason as above. - Moved classes directly related to parsed beatmaps (Beatmap, BeatmapSetList, BeatmapSetNode, OsuHitObject, and TimingPoint) into a new "beatmap" package. Signed-off-by: Jeffrey Han --- src/itdelatrisu/opsu/Container.java | 10 +- src/itdelatrisu/opsu/GameData.java | 42 +-- src/itdelatrisu/opsu/Options.java | 21 +- src/itdelatrisu/opsu/OsuParser.java | 242 ++++++++--------- src/itdelatrisu/opsu/SongSort.java | 61 +++-- src/itdelatrisu/opsu/UI.java | 2 +- src/itdelatrisu/opsu/Utils.java | 1 + .../opsu/audio/MusicController.java | 46 ++-- .../opsu/audio/SoundController.java | 2 +- .../{OsuFile.java => beatmap/Beatmap.java} | 25 +- .../BeatmapSetList.java} | 141 +++++----- .../BeatmapSetNode.java} | 142 +++++----- .../opsu/{ => beatmap}/OsuHitObject.java | 6 +- .../opsu/{ => beatmap}/TimingPoint.java | 2 +- .../opsu/db/{OsuDB.java => BeatmapDB.java} | 252 +++++++++--------- src/itdelatrisu/opsu/db/DBController.java | 4 +- src/itdelatrisu/opsu/db/ScoreDB.java | 46 ++-- .../opsu/downloads/DownloadNode.java | 4 +- src/itdelatrisu/opsu/objects/Circle.java | 2 +- src/itdelatrisu/opsu/objects/DummyObject.java | 2 +- src/itdelatrisu/opsu/objects/Slider.java | 12 +- src/itdelatrisu/opsu/objects/Spinner.java | 2 +- .../opsu/objects/curves/CatmullCurve.java | 2 +- .../objects/curves/CircumscribedCircle.java | 2 +- .../opsu/objects/curves/Curve.java | 2 +- .../curves/EqualDistanceMultiCurve.java | 2 +- .../opsu/objects/curves/LinearBezier.java | 2 +- src/itdelatrisu/opsu/replay/ReplayFrame.java | 2 +- src/itdelatrisu/opsu/states/ButtonMenu.java | 34 +-- .../opsu/states/DownloadsMenu.java | 14 +- src/itdelatrisu/opsu/states/Game.java | 166 ++++++------ .../opsu/states/GamePauseMenu.java | 4 +- src/itdelatrisu/opsu/states/GameRanking.java | 12 +- src/itdelatrisu/opsu/states/MainMenu.java | 32 +-- src/itdelatrisu/opsu/states/SongMenu.java | 194 +++++++------- src/itdelatrisu/opsu/states/Splash.java | 12 +- 36 files changed, 786 insertions(+), 761 deletions(-) rename src/itdelatrisu/opsu/{OsuFile.java => beatmap/Beatmap.java} (94%) rename src/itdelatrisu/opsu/{OsuGroupList.java => beatmap/BeatmapSetList.java} (75%) rename src/itdelatrisu/opsu/{OsuGroupNode.java => beatmap/BeatmapSetNode.java} (54%) rename src/itdelatrisu/opsu/{ => beatmap}/OsuHitObject.java (99%) rename src/itdelatrisu/opsu/{ => beatmap}/TimingPoint.java (99%) rename src/itdelatrisu/opsu/db/{OsuDB.java => BeatmapDB.java} (68%) diff --git a/src/itdelatrisu/opsu/Container.java b/src/itdelatrisu/opsu/Container.java index e4678f9e..9ce9de9f 100644 --- a/src/itdelatrisu/opsu/Container.java +++ b/src/itdelatrisu/opsu/Container.java @@ -19,6 +19,8 @@ package itdelatrisu.opsu; import itdelatrisu.opsu.audio.MusicController; +import itdelatrisu.opsu.beatmap.Beatmap; +import itdelatrisu.opsu.beatmap.BeatmapSetList; import itdelatrisu.opsu.downloads.DownloadList; import itdelatrisu.opsu.downloads.Updater; @@ -118,14 +120,14 @@ public class Container extends AppGameContainer { // reset image references GameImage.clearReferences(); GameData.Grade.clearReferences(); - OsuFile.resetImageCache(); + Beatmap.resetImageCache(); // prevent loading tracks from re-initializing OpenAL MusicController.reset(); - // reset OsuGroupList data - if (OsuGroupList.get() != null) - OsuGroupList.get().reset(); + // reset BeatmapSetList data + if (BeatmapSetList.get() != null) + BeatmapSetList.get().reset(); } @Override diff --git a/src/itdelatrisu/opsu/GameData.java b/src/itdelatrisu/opsu/GameData.java index effad0f1..715eaf38 100644 --- a/src/itdelatrisu/opsu/GameData.java +++ b/src/itdelatrisu/opsu/GameData.java @@ -22,6 +22,8 @@ import itdelatrisu.opsu.audio.HitSound; import itdelatrisu.opsu.audio.MusicController; import itdelatrisu.opsu.audio.SoundController; import itdelatrisu.opsu.audio.SoundEffect; +import itdelatrisu.opsu.beatmap.Beatmap; +import itdelatrisu.opsu.beatmap.OsuHitObject; import itdelatrisu.opsu.downloads.Updater; import itdelatrisu.opsu.objects.curves.Curve; import itdelatrisu.opsu.replay.Replay; @@ -334,7 +336,7 @@ public class GameData { /** * Constructor for score viewing. * This will initialize all parameters and images needed for the - * {@link #drawRankingElements(Graphics, OsuFile)} method. + * {@link #drawRankingElements(Graphics, Beatmap)} method. * @param s the ScoreData object * @param width container width * @param height container height @@ -582,8 +584,8 @@ public class GameData { width - margin, symbolHeight, 0.60f, 1f, true); // map progress circle - OsuFile osu = MusicController.getOsuFile(); - int firstObjectTime = osu.objects[0].getTime(); + Beatmap beatmap = MusicController.getBeatmap(); + int firstObjectTime = beatmap.objects[0].getTime(); int trackPosition = MusicController.getPosition(); float circleDiameter = symbolHeight * 0.60f; int circleX = (int) (width - margin - ( // max width: "100.00%" @@ -600,7 +602,7 @@ public class GameData { if (trackPosition > firstObjectTime) { // map progress (white) g.fillArc(circleX, symbolHeight, circleDiameter, circleDiameter, - -90, -90 + (int) (360f * (trackPosition - firstObjectTime) / (osu.endTime - firstObjectTime)) + -90, -90 + (int) (360f * (trackPosition - firstObjectTime) / (beatmap.endTime - firstObjectTime)) ); } else { // lead-in time (yellow) @@ -742,9 +744,9 @@ public class GameData { /** * Draws ranking elements: score, results, ranking, game mods. * @param g the graphics context - * @param osu the OsuFile + * @param beatmap the beatmap */ - public void drawRankingElements(Graphics g, OsuFile osu) { + public void drawRankingElements(Graphics g, Beatmap beatmap) { // TODO Version 2 skins float rankingHeight = 75; float scoreTextScale = 1.0f; @@ -825,9 +827,9 @@ public class GameData { rankingTitle.draw((width * 0.97f) - rankingTitle.getWidth(), 0); float marginX = width * 0.01f, marginY = height * 0.002f; Utils.FONT_LARGE.drawString(marginX, marginY, - String.format("%s - %s [%s]", osu.getArtist(), osu.getTitle(), osu.version), Color.white); + String.format("%s - %s [%s]", beatmap.getArtist(), beatmap.getTitle(), beatmap.version), Color.white); Utils.FONT_MEDIUM.drawString(marginX, marginY + Utils.FONT_LARGE.getLineHeight() - 6, - String.format("Beatmap by %s", osu.creator), Color.white); + String.format("Beatmap by %s", beatmap.creator), Color.white); Utils.FONT_MEDIUM.drawString(marginX, marginY + Utils.FONT_LARGE.getLineHeight() + Utils.FONT_MEDIUM.getLineHeight() - 10, String.format("Played on %s.", scoreData.getTimeString()), Color.white); @@ -1309,21 +1311,21 @@ public class GameData { * Returns a ScoreData object encapsulating all game data. * If score data already exists, the existing object will be returned * (i.e. this will not overwrite existing data). - * @param osu the OsuFile + * @param beatmap the beatmap * @return the ScoreData object */ - public ScoreData getScoreData(OsuFile osu) { + public ScoreData getScoreData(Beatmap beatmap) { if (scoreData != null) return scoreData; scoreData = new ScoreData(); scoreData.timestamp = System.currentTimeMillis() / 1000L; - scoreData.MID = osu.beatmapID; - scoreData.MSID = osu.beatmapSetID; - scoreData.title = osu.title; - scoreData.artist = osu.artist; - scoreData.creator = osu.creator; - scoreData.version = osu.version; + scoreData.MID = beatmap.beatmapID; + scoreData.MSID = beatmap.beatmapSetID; + scoreData.title = beatmap.title; + scoreData.artist = beatmap.artist; + scoreData.creator = beatmap.creator; + scoreData.version = beatmap.version; scoreData.hit300 = hitResultCount[HIT_300]; scoreData.hit100 = hitResultCount[HIT_100]; scoreData.hit50 = hitResultCount[HIT_50]; @@ -1342,10 +1344,10 @@ public class GameData { * Returns a Replay object encapsulating all game data. * If a replay already exists and frames is null, the existing object will be returned. * @param frames the replay frames - * @param osu the associated OsuFile + * @param beatmap the associated beatmap * @return the Replay object, or null if none exists and frames is null */ - public Replay getReplay(ReplayFrame[] frames, OsuFile osu) { + public Replay getReplay(ReplayFrame[] frames, Beatmap beatmap) { if (replay != null && frames == null) return replay; @@ -1353,9 +1355,9 @@ public class GameData { return null; replay = new Replay(); - replay.mode = OsuFile.MODE_OSU; + replay.mode = Beatmap.MODE_OSU; replay.version = Updater.get().getBuildDate(); - replay.beatmapHash = (osu == null) ? "" : Utils.getMD5(osu.getFile()); + replay.beatmapHash = (beatmap == null) ? "" : Utils.getMD5(beatmap.getFile()); replay.playerName = ""; // TODO replay.replayHash = Long.toString(System.currentTimeMillis()); // TODO replay.hit300 = (short) hitResultCount[HIT_300]; diff --git a/src/itdelatrisu/opsu/Options.java b/src/itdelatrisu/opsu/Options.java index 28a8f2a6..ef5b620e 100644 --- a/src/itdelatrisu/opsu/Options.java +++ b/src/itdelatrisu/opsu/Options.java @@ -19,6 +19,7 @@ package itdelatrisu.opsu; import itdelatrisu.opsu.audio.MusicController; +import itdelatrisu.opsu.beatmap.Beatmap; import java.io.BufferedReader; import java.io.BufferedWriter; @@ -63,7 +64,7 @@ public class Options { }; /** Cached beatmap database name. */ - public static final File OSU_DB = new File(DATA_DIR, ".opsu.db"); + public static final File BEATMAP_DB = new File(DATA_DIR, ".opsu.db"); /** Score database name. */ public static final File SCORE_DB = new File(DATA_DIR, ".opsu_scores.db"); @@ -866,28 +867,28 @@ public class Options { } /** - * Returns a dummy OsuFile containing the theme song. - * @return the theme song OsuFile + * Returns a dummy Beatmap containing the theme song. + * @return the theme song beatmap */ - public static OsuFile getOsuTheme() { + public static Beatmap getThemeBeatmap() { String[] tokens = themeString.split(","); if (tokens.length != 4) { ErrorHandler.error("Theme song string is malformed.", null, false); return null; } - OsuFile osu = new OsuFile(null); - osu.audioFilename = new File(tokens[0]); - osu.title = tokens[1]; - osu.artist = tokens[2]; + Beatmap beatmap = new Beatmap(null); + beatmap.audioFilename = new File(tokens[0]); + beatmap.title = tokens[1]; + beatmap.artist = tokens[2]; try { - osu.endTime = Integer.parseInt(tokens[3]); + beatmap.endTime = Integer.parseInt(tokens[3]); } catch (NumberFormatException e) { ErrorHandler.error("Theme song length is not a valid integer", e, false); return null; } - return osu; + return beatmap; } /** diff --git a/src/itdelatrisu/opsu/OsuParser.java b/src/itdelatrisu/opsu/OsuParser.java index 943d232d..7eaeaa5e 100644 --- a/src/itdelatrisu/opsu/OsuParser.java +++ b/src/itdelatrisu/opsu/OsuParser.java @@ -18,7 +18,12 @@ package itdelatrisu.opsu; -import itdelatrisu.opsu.db.OsuDB; +import itdelatrisu.opsu.beatmap.Beatmap; +import itdelatrisu.opsu.beatmap.BeatmapSetList; +import itdelatrisu.opsu.beatmap.BeatmapSetNode; +import itdelatrisu.opsu.beatmap.OsuHitObject; +import itdelatrisu.opsu.beatmap.TimingPoint; +import itdelatrisu.opsu.db.BeatmapDB; import java.io.BufferedReader; import java.io.File; @@ -67,12 +72,12 @@ public class OsuParser { /** * Invokes parser for each OSU file in a root directory and - * adds the OsuFiles to a new OsuGroupList. + * adds the beatmaps to a new BeatmapSetList. * @param root the root directory (search has depth 1) */ public static void parseAllFiles(File root) { - // create a new OsuGroupList - OsuGroupList.create(); + // create a new BeatmapSetList + BeatmapSetList.create(); // parse all directories parseDirectories(root.listFiles()); @@ -80,11 +85,11 @@ public class OsuParser { /** * Invokes parser for each directory in the given array and - * adds the OsuFiles to the existing OsuGroupList. + * adds the beatmaps to the existing BeatmapSetList. * @param dirs the array of directories to parse - * @return the last OsuGroupNode parsed, or null if none + * @return the last BeatmapSetNode parsed, or null if none */ - public static OsuGroupNode parseDirectories(File[] dirs) { + public static BeatmapSetNode parseDirectories(File[] dirs) { if (dirs == null) return null; @@ -94,15 +99,15 @@ public class OsuParser { totalDirectories = dirs.length; // get last modified map from database - Map map = OsuDB.getLastModifiedMap(); + Map map = BeatmapDB.getLastModifiedMap(); - // OsuFile lists - List> allOsuFiles = new LinkedList>(); - List cachedOsuFiles = new LinkedList(); // loaded from database - List parsedOsuFiles = new LinkedList(); // loaded from parser + // beatmap lists + List> allBeatmaps = new LinkedList>(); + List cachedBeatmaps = new LinkedList(); // loaded from database + List parsedBeatmaps = new LinkedList(); // loaded from parser // parse directories - OsuGroupNode lastNode = null; + BeatmapSetNode lastNode = null; for (File dir : dirs) { currentDirectoryIndex++; if (!dir.isDirectory()) @@ -119,7 +124,7 @@ public class OsuParser { continue; // create a new group entry - ArrayList osuFiles = new ArrayList(); + ArrayList beatmaps = new ArrayList(); for (File file : files) { currentFile = file; @@ -130,29 +135,29 @@ public class OsuParser { long lastModified = map.get(path); if (lastModified == file.lastModified()) { // add to cached beatmap list - OsuFile osu = new OsuFile(file); - osuFiles.add(osu); - cachedOsuFiles.add(osu); + Beatmap beatmap = new Beatmap(file); + beatmaps.add(beatmap); + cachedBeatmaps.add(beatmap); continue; } else - OsuDB.delete(dir.getName(), file.getName()); + BeatmapDB.delete(dir.getName(), file.getName()); } // Parse hit objects only when needed to save time/memory. // Change boolean to 'true' to parse them immediately. - OsuFile osu = parseFile(file, dir, osuFiles, false); + Beatmap beatmap = parseFile(file, dir, beatmaps, false); // add to parsed beatmap list - if (osu != null) { - osuFiles.add(osu); - parsedOsuFiles.add(osu); + if (beatmap != null) { + beatmaps.add(beatmap); + parsedBeatmaps.add(beatmap); } } // add group entry if non-empty - if (!osuFiles.isEmpty()) { - osuFiles.trimToSize(); - allOsuFiles.add(osuFiles); + if (!beatmaps.isEmpty()) { + beatmaps.trimToSize(); + allBeatmaps.add(beatmaps); } // stop parsing files (interrupted) @@ -161,27 +166,27 @@ public class OsuParser { } // load cached entries from database - if (!cachedOsuFiles.isEmpty()) { + if (!cachedBeatmaps.isEmpty()) { status = Status.CACHE; // Load array fields only when needed to save time/memory. // Change flag to 'LOAD_ALL' to load them immediately. - OsuDB.load(cachedOsuFiles, OsuDB.LOAD_NONARRAY); + BeatmapDB.load(cachedBeatmaps, BeatmapDB.LOAD_NONARRAY); } - // add group entries to OsuGroupList - for (ArrayList osuFiles : allOsuFiles) { - Collections.sort(osuFiles); - lastNode = OsuGroupList.get().addSongGroup(osuFiles); + // add group entries to BeatmapSetList + for (ArrayList beatmaps : allBeatmaps) { + Collections.sort(beatmaps); + lastNode = BeatmapSetList.get().addSongGroup(beatmaps); } // clear string DB stringdb = new HashMap(); // add beatmap entries to database - if (!parsedOsuFiles.isEmpty()) { + if (!parsedBeatmaps.isEmpty()) { status = Status.INSERTING; - OsuDB.insert(parsedOsuFiles); + BeatmapDB.insert(parsedBeatmaps); } status = Status.NONE; @@ -192,16 +197,16 @@ public class OsuParser { } /** - * Parses an OSU file. + * Parses a beatmap. * @param file the file to parse * @param dir the directory containing the beatmap - * @param osuFiles the song group + * @param beatmaps the song group * @param parseObjects if true, hit objects will be fully parsed now - * @return the new OsuFile object + * @return the new beatmap */ - private static OsuFile parseFile(File file, File dir, ArrayList osuFiles, boolean parseObjects) { - OsuFile osu = new OsuFile(file); - osu.timingPoints = new ArrayList(); + private static Beatmap parseFile(File file, File dir, ArrayList beatmaps, boolean parseObjects) { + Beatmap beatmap = new Beatmap(file); + beatmap.timingPoints = new ArrayList(); try (BufferedReader in = new BufferedReader(new InputStreamReader(new FileInputStream(file), "UTF-8"))) { String line = in.readLine(); @@ -226,9 +231,9 @@ public class OsuParser { switch (tokens[0]) { case "AudioFilename": File audioFileName = new File(dir, tokens[1]); - if (!osuFiles.isEmpty()) { - // if possible, reuse the same File object from another OsuFile in the group - File groupAudioFileName = osuFiles.get(0).audioFilename; + if (!beatmaps.isEmpty()) { + // if possible, reuse the same File object from another Beatmap in the group + File groupAudioFileName = beatmaps.get(0).audioFilename; if (groupAudioFileName != null && tokens[1].equalsIgnoreCase(groupAudioFileName.getName())) audioFileName = groupAudioFileName; @@ -248,42 +253,42 @@ public class OsuParser { return null; } } - osu.audioFilename = audioFileName; + beatmap.audioFilename = audioFileName; break; case "AudioLeadIn": - osu.audioLeadIn = Integer.parseInt(tokens[1]); + beatmap.audioLeadIn = Integer.parseInt(tokens[1]); break; // case "AudioHash": // deprecated -// osu.audioHash = tokens[1]; +// beatmap.audioHash = tokens[1]; // break; case "PreviewTime": - osu.previewTime = Integer.parseInt(tokens[1]); + beatmap.previewTime = Integer.parseInt(tokens[1]); break; case "Countdown": - osu.countdown = Byte.parseByte(tokens[1]); + beatmap.countdown = Byte.parseByte(tokens[1]); break; case "SampleSet": - osu.sampleSet = getDBString(tokens[1]); + beatmap.sampleSet = getDBString(tokens[1]); break; case "StackLeniency": - osu.stackLeniency = Float.parseFloat(tokens[1]); + beatmap.stackLeniency = Float.parseFloat(tokens[1]); break; case "Mode": - osu.mode = Byte.parseByte(tokens[1]); + beatmap.mode = Byte.parseByte(tokens[1]); /* Non-Opsu! standard files not implemented (obviously). */ - if (osu.mode != OsuFile.MODE_OSU) + if (beatmap.mode != Beatmap.MODE_OSU) return null; break; case "LetterboxInBreaks": - osu.letterboxInBreaks = (Integer.parseInt(tokens[1]) == 1); + beatmap.letterboxInBreaks = (Integer.parseInt(tokens[1]) == 1); break; case "WidescreenStoryboard": - osu.widescreenStoryboard = (Integer.parseInt(tokens[1]) == 1); + beatmap.widescreenStoryboard = (Integer.parseInt(tokens[1]) == 1); break; case "EpilepsyWarning": - osu.epilepsyWarning = (Integer.parseInt(tokens[1]) == 1); + beatmap.epilepsyWarning = (Integer.parseInt(tokens[1]) == 1); default: break; } @@ -307,21 +312,21 @@ public class OsuParser { // switch (tokens[0]) { // case "Bookmarks": // String[] bookmarks = tokens[1].split(","); -// osu.bookmarks = new int[bookmarks.length]; +// beatmap.bookmarks = new int[bookmarks.length]; // for (int i = 0; i < bookmarks.length; i++) // osu.bookmarks[i] = Integer.parseInt(bookmarks[i]); // break; // case "DistanceSpacing": -// osu.distanceSpacing = Float.parseFloat(tokens[1]); +// beatmap.distanceSpacing = Float.parseFloat(tokens[1]); // break; // case "BeatDivisor": -// osu.beatDivisor = Byte.parseByte(tokens[1]); +// beatmap.beatDivisor = Byte.parseByte(tokens[1]); // break; // case "GridSize": -// osu.gridSize = Integer.parseInt(tokens[1]); +// beatmap.gridSize = Integer.parseInt(tokens[1]); // break; // case "TimelineZoom": -// osu.timelineZoom = Integer.parseInt(tokens[1]); +// beatmap.timelineZoom = Integer.parseInt(tokens[1]); // break; // default: // break; @@ -344,45 +349,45 @@ public class OsuParser { try { switch (tokens[0]) { case "Title": - osu.title = getDBString(tokens[1]); + beatmap.title = getDBString(tokens[1]); break; case "TitleUnicode": - osu.titleUnicode = getDBString(tokens[1]); + beatmap.titleUnicode = getDBString(tokens[1]); break; case "Artist": - osu.artist = getDBString(tokens[1]); + beatmap.artist = getDBString(tokens[1]); break; case "ArtistUnicode": - osu.artistUnicode = getDBString(tokens[1]); + beatmap.artistUnicode = getDBString(tokens[1]); break; case "Creator": - osu.creator = getDBString(tokens[1]); + beatmap.creator = getDBString(tokens[1]); break; case "Version": - osu.version = getDBString(tokens[1]); + beatmap.version = getDBString(tokens[1]); break; case "Source": - osu.source = getDBString(tokens[1]); + beatmap.source = getDBString(tokens[1]); break; case "Tags": - osu.tags = getDBString(tokens[1].toLowerCase()); + beatmap.tags = getDBString(tokens[1].toLowerCase()); break; case "BeatmapID": - osu.beatmapID = Integer.parseInt(tokens[1]); + beatmap.beatmapID = Integer.parseInt(tokens[1]); break; case "BeatmapSetID": - osu.beatmapSetID = Integer.parseInt(tokens[1]); + beatmap.beatmapSetID = Integer.parseInt(tokens[1]); break; } } catch (Exception e) { Log.warn(String.format("Failed to read metadata '%s' for file '%s'.", line, file.getAbsolutePath()), e); } - if (osu.beatmapSetID <= 0) { // try to determine MSID from directory name + if (beatmap.beatmapSetID <= 0) { // try to determine MSID from directory name if (dir != null && dir.isDirectory()) { String dirName = dir.getName(); if (!dirName.isEmpty() && dirName.matches(DIR_MSID_PATTERN)) - osu.beatmapSetID = Integer.parseInt(dirName.substring(0, dirName.indexOf(' '))); + beatmap.beatmapSetID = Integer.parseInt(dirName.substring(0, dirName.indexOf(' '))); } } } @@ -399,22 +404,22 @@ public class OsuParser { try { switch (tokens[0]) { case "HPDrainRate": - osu.HPDrainRate = Float.parseFloat(tokens[1]); + beatmap.HPDrainRate = Float.parseFloat(tokens[1]); break; case "CircleSize": - osu.circleSize = Float.parseFloat(tokens[1]); + beatmap.circleSize = Float.parseFloat(tokens[1]); break; case "OverallDifficulty": - osu.overallDifficulty = Float.parseFloat(tokens[1]); + beatmap.overallDifficulty = Float.parseFloat(tokens[1]); break; case "ApproachRate": - osu.approachRate = Float.parseFloat(tokens[1]); + beatmap.approachRate = Float.parseFloat(tokens[1]); break; case "SliderMultiplier": - osu.sliderMultiplier = Float.parseFloat(tokens[1]); + beatmap.sliderMultiplier = Float.parseFloat(tokens[1]); break; case "SliderTickRate": - osu.sliderTickRate = Float.parseFloat(tokens[1]); + beatmap.sliderTickRate = Float.parseFloat(tokens[1]); break; } } catch (Exception e) { @@ -422,8 +427,8 @@ public class OsuParser { line, file.getAbsolutePath()), e); } } - if (osu.approachRate == -1f) // not in old format - osu.approachRate = osu.overallDifficulty; + if (beatmap.approachRate == -1f) // not in old format + beatmap.approachRate = beatmap.overallDifficulty; break; case "[Events]": while ((line = in.readLine()) != null) { @@ -438,14 +443,14 @@ public class OsuParser { tokens[2] = tokens[2].replaceAll("^\"|\"$", ""); String ext = OsuParser.getExtension(tokens[2]); if (ext.equals("jpg") || ext.equals("png")) - osu.bg = getDBString(tokens[2]); + beatmap.bg = getDBString(tokens[2]); break; case "2": // break periods try { - if (osu.breaks == null) // optional, create if needed - osu.breaks = new ArrayList(); - osu.breaks.add(Integer.parseInt(tokens[1])); - osu.breaks.add(Integer.parseInt(tokens[2])); + if (beatmap.breaks == null) // optional, create if needed + beatmap.breaks = new ArrayList(); + beatmap.breaks.add(Integer.parseInt(tokens[1])); + beatmap.breaks.add(Integer.parseInt(tokens[2])); } catch (Exception e) { Log.warn(String.format("Failed to read break period '%s' for file '%s'.", line, file.getAbsolutePath()), e); @@ -456,8 +461,8 @@ public class OsuParser { break; } } - if (osu.breaks != null) - osu.breaks.trimToSize(); + if (beatmap.breaks != null) + beatmap.breaks.trimToSize(); break; case "[TimingPoints]": while ((line = in.readLine()) != null) { @@ -474,21 +479,21 @@ public class OsuParser { // calculate BPM if (!timingPoint.isInherited()) { int bpm = Math.round(60000 / timingPoint.getBeatLength()); - if (osu.bpmMin == 0) - osu.bpmMin = osu.bpmMax = bpm; - else if (bpm < osu.bpmMin) - osu.bpmMin = bpm; - else if (bpm > osu.bpmMax) - osu.bpmMax = bpm; + if (beatmap.bpmMin == 0) + beatmap.bpmMin = beatmap.bpmMax = bpm; + else if (bpm < beatmap.bpmMin) + beatmap.bpmMin = bpm; + else if (bpm > beatmap.bpmMax) + beatmap.bpmMax = bpm; } - osu.timingPoints.add(timingPoint); + beatmap.timingPoints.add(timingPoint); } catch (Exception e) { Log.warn(String.format("Failed to read timing point '%s' for file '%s'.", line, file.getAbsolutePath()), e); } } - osu.timingPoints.trimToSize(); + beatmap.timingPoints.trimToSize(); break; case "[Colours]": LinkedList colors = new LinkedList(); @@ -525,7 +530,7 @@ public class OsuParser { } } if (!colors.isEmpty()) - osu.combo = colors.toArray(new Color[colors.size()]); + beatmap.combo = colors.toArray(new Color[colors.size()]); break; case "[HitObjects]": int type = 0; @@ -540,11 +545,11 @@ public class OsuParser { try { type = Integer.parseInt(tokens[3]); if ((type & OsuHitObject.TYPE_CIRCLE) > 0) - osu.hitObjectCircle++; + beatmap.hitObjectCircle++; else if ((type & OsuHitObject.TYPE_SLIDER) > 0) - osu.hitObjectSlider++; + beatmap.hitObjectSlider++; else //if ((type & OsuHitObject.TYPE_SPINNER) > 0) - osu.hitObjectSpinner++; + beatmap.hitObjectSpinner++; } catch (Exception e) { Log.warn(String.format("Failed to read hit object '%s' for file '%s'.", line, file.getAbsolutePath()), e); @@ -558,9 +563,9 @@ public class OsuParser { int index = tokens[5].indexOf(':'); if (index != -1) tokens[5] = tokens[5].substring(0, index); - osu.endTime = Integer.parseInt(tokens[5]); + beatmap.endTime = Integer.parseInt(tokens[5]); } else if (type != 0) - osu.endTime = Integer.parseInt(tokens[2]); + beatmap.endTime = Integer.parseInt(tokens[2]); } catch (Exception e) { Log.warn(String.format("Failed to read hit object end time '%s' for file '%s'.", line, file.getAbsolutePath()), e); @@ -576,32 +581,31 @@ public class OsuParser { } // no associated audio file? - if (osu.audioFilename == null) + if (beatmap.audioFilename == null) return null; // if no custom colors, use the default color scheme - if (osu.combo == null) - osu.combo = Utils.DEFAULT_COMBO; + if (beatmap.combo == null) + beatmap.combo = Utils.DEFAULT_COMBO; // parse hit objects now? if (parseObjects) - parseHitObjects(osu); + parseHitObjects(beatmap); - return osu; + return beatmap; } /** - * Parses all hit objects in an OSU file. - * @param osu the OsuFile to parse + * Parses all hit objects in a beatmap. + * @param beatmap the beatmap to parse */ - public static void parseHitObjects(OsuFile osu) { - if (osu.objects != null) // already parsed + public static void parseHitObjects(Beatmap beatmap) { + if (beatmap.objects != null) // already parsed return; - osu.objects = new OsuHitObject[(osu.hitObjectCircle - + osu.hitObjectSlider + osu.hitObjectSpinner)]; + beatmap.objects = new OsuHitObject[(beatmap.hitObjectCircle + beatmap.hitObjectSlider + beatmap.hitObjectSpinner)]; - try (BufferedReader in = new BufferedReader(new FileReader(osu.getFile()))) { + try (BufferedReader in = new BufferedReader(new FileReader(beatmap.getFile()))) { String line = in.readLine(); while (line != null) { line = line.trim(); @@ -611,7 +615,7 @@ public class OsuParser { break; } if (line == null) { - Log.warn(String.format("No hit objects found in OsuFile '%s'.", osu.toString())); + Log.warn(String.format("No hit objects found in Beatmap '%s'.", beatmap.toString())); return; } @@ -621,7 +625,7 @@ public class OsuParser { int objectIndex = 0; boolean first = true; - while ((line = in.readLine()) != null && objectIndex < osu.objects.length) { + while ((line = in.readLine()) != null && objectIndex < beatmap.objects.length) { line = line.trim(); if (!isValidLine(line)) continue; @@ -643,7 +647,7 @@ public class OsuParser { if (hitObject.isNewCombo() || first) { int skip = (hitObject.isSpinner() ? 0 : 1) + hitObject.getComboSkip(); for (int i = 0; i < skip; i++) { - comboIndex = (comboIndex + 1) % osu.combo.length; + comboIndex = (comboIndex + 1) % beatmap.combo.length; comboNumber = 1; } first = false; @@ -652,14 +656,14 @@ public class OsuParser { hitObject.setComboIndex(comboIndex); hitObject.setComboNumber(comboNumber++); - osu.objects[objectIndex++] = hitObject; + beatmap.objects[objectIndex++] = hitObject; } catch (Exception e) { - Log.warn(String.format("Failed to read hit object '%s' for OsuFile '%s'.", - line, osu.toString()), e); + Log.warn(String.format("Failed to read hit object '%s' for Beatmap '%s'.", + line, beatmap.toString()), e); } } } catch (IOException e) { - ErrorHandler.error(String.format("Failed to read file '%s'.", osu.getFile().getAbsolutePath()), e, false); + ErrorHandler.error(String.format("Failed to read file '%s'.", beatmap.getFile().getAbsolutePath()), e, false); } } diff --git a/src/itdelatrisu/opsu/SongSort.java b/src/itdelatrisu/opsu/SongSort.java index db0c69a2..beeac0b9 100644 --- a/src/itdelatrisu/opsu/SongSort.java +++ b/src/itdelatrisu/opsu/SongSort.java @@ -18,6 +18,9 @@ package itdelatrisu.opsu; +import itdelatrisu.opsu.beatmap.Beatmap; +import itdelatrisu.opsu.beatmap.BeatmapSetNode; + import java.util.Arrays; import java.util.Collections; import java.util.Comparator; @@ -25,7 +28,7 @@ import java.util.Comparator; import org.newdawn.slick.Image; /** - * OsuGroupNode sorts. + * BeatmapSetNode sorts. */ public enum SongSort { TITLE (0, "Title", new TitleOrder()), @@ -41,7 +44,7 @@ public enum SongSort { private String name; /** The comparator for the sort. */ - private Comparator comparator; + private Comparator comparator; /** The tab associated with the sort (displayed in Song Menu screen). */ private MenuButton tab; @@ -72,60 +75,60 @@ public enum SongSort { public static void setSort(SongSort sort) { SongSort.currentSort = sort; } /** - * Compares two OsuGroupNode objects by title. + * Compares two BeatmapSetNode objects by title. */ - private static class TitleOrder implements Comparator { + private static class TitleOrder implements Comparator { @Override - public int compare(OsuGroupNode v, OsuGroupNode w) { - return v.osuFiles.get(0).title.compareToIgnoreCase(w.osuFiles.get(0).title); + public int compare(BeatmapSetNode v, BeatmapSetNode w) { + return v.beatmaps.get(0).title.compareToIgnoreCase(w.beatmaps.get(0).title); } } /** - * Compares two OsuGroupNode objects by artist. + * Compares two BeatmapSetNode objects by artist. */ - private static class ArtistOrder implements Comparator { + private static class ArtistOrder implements Comparator { @Override - public int compare(OsuGroupNode v, OsuGroupNode w) { - return v.osuFiles.get(0).artist.compareToIgnoreCase(w.osuFiles.get(0).artist); + public int compare(BeatmapSetNode v, BeatmapSetNode w) { + return v.beatmaps.get(0).artist.compareToIgnoreCase(w.beatmaps.get(0).artist); } } /** - * Compares two OsuGroupNode objects by creator. + * Compares two BeatmapSetNode objects by creator. */ - private static class CreatorOrder implements Comparator { + private static class CreatorOrder implements Comparator { @Override - public int compare(OsuGroupNode v, OsuGroupNode w) { - return v.osuFiles.get(0).creator.compareToIgnoreCase(w.osuFiles.get(0).creator); + public int compare(BeatmapSetNode v, BeatmapSetNode w) { + return v.beatmaps.get(0).creator.compareToIgnoreCase(w.beatmaps.get(0).creator); } } /** - * Compares two OsuGroupNode objects by BPM. + * Compares two BeatmapSetNode objects by BPM. */ - private static class BPMOrder implements Comparator { + private static class BPMOrder implements Comparator { @Override - public int compare(OsuGroupNode v, OsuGroupNode w) { - return Integer.compare(v.osuFiles.get(0).bpmMax, w.osuFiles.get(0).bpmMax); + public int compare(BeatmapSetNode v, BeatmapSetNode w) { + return Integer.compare(v.beatmaps.get(0).bpmMax, w.beatmaps.get(0).bpmMax); } } /** - * Compares two OsuGroupNode objects by length. + * Compares two BeatmapSetNode objects by length. * Uses the longest beatmap in each set for comparison. */ - private static class LengthOrder implements Comparator { + private static class LengthOrder implements Comparator { @Override - public int compare(OsuGroupNode v, OsuGroupNode w) { + public int compare(BeatmapSetNode v, BeatmapSetNode w) { int vMax = 0, wMax = 0; - for (OsuFile osu : v.osuFiles) { - if (osu.endTime > vMax) - vMax = osu.endTime; + for (Beatmap beatmap : v.beatmaps) { + if (beatmap.endTime > vMax) + vMax = beatmap.endTime; } - for (OsuFile osu : w.osuFiles) { - if (osu.endTime > wMax) - wMax = osu.endTime; + for (Beatmap beatmap : w.beatmaps) { + if (beatmap.endTime > wMax) + wMax = beatmap.endTime; } return Integer.compare(vMax, wMax); } @@ -137,7 +140,7 @@ public enum SongSort { * @param name the sort name * @param comparator the comparator for the sort */ - SongSort(int id, String name, Comparator comparator) { + SongSort(int id, String name, Comparator comparator) { this.id = id; this.name = name; this.comparator = comparator; @@ -167,7 +170,7 @@ public enum SongSort { * Returns the comparator for the sort. * @return the comparator */ - public Comparator getComparator() { return comparator; } + public Comparator getComparator() { return comparator; } /** * Checks if the coordinates are within the image bounds. diff --git a/src/itdelatrisu/opsu/UI.java b/src/itdelatrisu/opsu/UI.java index fd5c5792..ed14be98 100644 --- a/src/itdelatrisu/opsu/UI.java +++ b/src/itdelatrisu/opsu/UI.java @@ -483,7 +483,7 @@ public class UI { } /** - * Draws loading progress (OSZ unpacking, OsuFile parsing, sound loading) + * Draws loading progress (OSZ unpacking, beatmap parsing, sound loading) * at the bottom of the screen. */ public static void drawLoadingProgress(Graphics g) { diff --git a/src/itdelatrisu/opsu/Utils.java b/src/itdelatrisu/opsu/Utils.java index bfa75efe..653a4594 100644 --- a/src/itdelatrisu/opsu/Utils.java +++ b/src/itdelatrisu/opsu/Utils.java @@ -20,6 +20,7 @@ package itdelatrisu.opsu; import itdelatrisu.opsu.audio.SoundController; import itdelatrisu.opsu.audio.SoundEffect; +import itdelatrisu.opsu.beatmap.OsuHitObject; import itdelatrisu.opsu.downloads.Download; import itdelatrisu.opsu.downloads.DownloadNode; import itdelatrisu.opsu.replay.PlaybackSpeed; diff --git a/src/itdelatrisu/opsu/audio/MusicController.java b/src/itdelatrisu/opsu/audio/MusicController.java index c8de37dd..e0f9e7dc 100644 --- a/src/itdelatrisu/opsu/audio/MusicController.java +++ b/src/itdelatrisu/opsu/audio/MusicController.java @@ -20,8 +20,8 @@ package itdelatrisu.opsu.audio; import itdelatrisu.opsu.ErrorHandler; import itdelatrisu.opsu.Options; -import itdelatrisu.opsu.OsuFile; import itdelatrisu.opsu.OsuParser; +import itdelatrisu.opsu.beatmap.Beatmap; import java.io.File; import java.io.IOException; @@ -50,8 +50,8 @@ public class MusicController { /** The current music track. */ private static Music player; - /** The last OsuFile passed to play(). */ - private static OsuFile lastOsu; + /** The last beatmap passed to play(). */ + private static Beatmap lastBeatmap; /** The track duration. */ private static int duration = 0; @@ -80,23 +80,23 @@ public class MusicController { /** * Plays an audio file at the preview position. * If the audio file is already playing, then nothing will happen. - * @param osu the OsuFile to play + * @param beatmap the beatmap to play * @param loop whether or not to loop the track * @param preview whether to start at the preview time (true) or beginning (false) */ - public static void play(final OsuFile osu, final boolean loop, final boolean preview) { + public static void play(final Beatmap beatmap, final boolean loop, final boolean preview) { // new track: load and play - if (lastOsu == null || !osu.audioFilename.equals(lastOsu.audioFilename)) { + if (lastBeatmap == null || !beatmap.audioFilename.equals(lastBeatmap.audioFilename)) { reset(); System.gc(); - switch (OsuParser.getExtension(osu.audioFilename.getName())) { + switch (OsuParser.getExtension(beatmap.audioFilename.getName())) { case "ogg": case "mp3": trackLoader = new Thread() { @Override public void run() { - loadTrack(osu.audioFilename, (preview) ? osu.previewTime : 0, loop); + loadTrack(beatmap.audioFilename, (preview) ? beatmap.previewTime : 0, loop); } }; trackLoader.start(); @@ -107,10 +107,10 @@ public class MusicController { } // new track position: play at position - else if (osu.previewTime != lastOsu.previewTime) - playAt(osu.previewTime, loop); + else if (beatmap.previewTime != lastBeatmap.previewTime) + playAt(beatmap.previewTime, loop); - lastOsu = osu; + lastBeatmap = beatmap; } /** @@ -170,9 +170,9 @@ public class MusicController { public static boolean trackExists() { return (player != null); } /** - * Returns the OsuFile associated with the current track. + * Returns the beatmap associated with the current track. */ - public static OsuFile getOsuFile() { return lastOsu; } + public static Beatmap getBeatmap() { return lastBeatmap; } /** * Returns true if the current track is playing. @@ -251,17 +251,17 @@ public class MusicController { * Returns the duration of the current track, in milliseconds. * Currently only works for MP3s. * @return the duration, or -1 if no track exists, else the {@code endTime} - * field of the OsuFile loaded + * field of the beatmap loaded * @author Tom Brito (http://stackoverflow.com/a/3056161) */ public static int getDuration() { - if (!trackExists() || lastOsu == null) + if (!trackExists() || lastBeatmap == null) return -1; if (duration == 0) { - if (lastOsu.audioFilename.getName().endsWith(".mp3")) { + if (lastBeatmap.audioFilename.getName().endsWith(".mp3")) { try { - AudioFileFormat fileFormat = AudioSystem.getAudioFileFormat(lastOsu.audioFilename); + AudioFileFormat fileFormat = AudioSystem.getAudioFileFormat(lastBeatmap.audioFilename); if (fileFormat instanceof TAudioFileFormat) { Map properties = ((TAudioFileFormat) fileFormat).properties(); Long microseconds = (Long) properties.get("duration"); @@ -270,7 +270,7 @@ public class MusicController { } } catch (UnsupportedAudioFileException | IOException e) {} } - duration = lastOsu.endTime; + duration = lastBeatmap.endTime; } return duration; } @@ -316,16 +316,16 @@ public class MusicController { */ public static void loopTrackIfEnded(boolean preview) { if (trackEnded && trackExists()) - playAt((preview) ? lastOsu.previewTime : 0, false); + playAt((preview) ? lastBeatmap.previewTime : 0, false); } /** * Plays the theme song. */ public static void playThemeSong() { - OsuFile osu = Options.getOsuTheme(); - if (osu != null) { - play(osu, true, false); + Beatmap beatmap = Options.getThemeBeatmap(); + if (beatmap != null) { + play(beatmap, true, false); themePlaying = true; } } @@ -376,7 +376,7 @@ public class MusicController { trackLoader = null; // reset state - lastOsu = null; + lastBeatmap = null; duration = 0; trackEnded = false; themePlaying = false; diff --git a/src/itdelatrisu/opsu/audio/SoundController.java b/src/itdelatrisu/opsu/audio/SoundController.java index 20eb82b4..04d1dada 100644 --- a/src/itdelatrisu/opsu/audio/SoundController.java +++ b/src/itdelatrisu/opsu/audio/SoundController.java @@ -20,8 +20,8 @@ package itdelatrisu.opsu.audio; import itdelatrisu.opsu.ErrorHandler; import itdelatrisu.opsu.Options; -import itdelatrisu.opsu.OsuHitObject; import itdelatrisu.opsu.audio.HitSound.SampleSet; +import itdelatrisu.opsu.beatmap.OsuHitObject; import java.io.File; import java.io.IOException; diff --git a/src/itdelatrisu/opsu/OsuFile.java b/src/itdelatrisu/opsu/beatmap/Beatmap.java similarity index 94% rename from src/itdelatrisu/opsu/OsuFile.java rename to src/itdelatrisu/opsu/beatmap/Beatmap.java index b1ee9b4f..d5cc236d 100644 --- a/src/itdelatrisu/opsu/OsuFile.java +++ b/src/itdelatrisu/opsu/beatmap/Beatmap.java @@ -16,7 +16,10 @@ * along with opsu!. If not, see . */ -package itdelatrisu.opsu; +package itdelatrisu.opsu.beatmap; + +import itdelatrisu.opsu.Options; +import itdelatrisu.opsu.Utils; import java.io.File; import java.util.ArrayList; @@ -29,19 +32,19 @@ import org.newdawn.slick.SlickException; import org.newdawn.slick.util.Log; /** - * Data type storing parsed data from OSU files. + * Beatmap structure storing data parsed from OSU files. */ -public class OsuFile implements Comparable { +public class Beatmap implements Comparable { /** Game modes. */ public static final byte MODE_OSU = 0, MODE_TAIKO = 1, MODE_CTB = 2, MODE_MANIA = 3; /** Map of all loaded background images. */ - private static HashMap bgImageMap = new HashMap(); + private static HashMap bgImageMap = new HashMap(); /** Maximum number of cached images before all get erased. */ private static final int MAX_CACHE_SIZE = 10; - /** The OSU File object associated with this OsuFile. */ + /** The OSU File object associated with this beatmap. */ private File file; /** @@ -217,14 +220,14 @@ public class OsuFile implements Comparable { * This does NOT destroy images, so be careful of memory leaks! */ public static void resetImageCache() { - bgImageMap = new HashMap(); + bgImageMap = new HashMap(); } /** * Constructor. - * @param file the file associated with this OsuFile + * @param file the file associated with this beatmap */ - public OsuFile(File file) { + public Beatmap(File file) { this.file = file; } @@ -253,7 +256,7 @@ public class OsuFile implements Comparable { } /** - * Draws the background associated with the OsuFile. + * Draws the beatmap background. * @param width the container width * @param height the container height * @param alpha the alpha value @@ -300,10 +303,10 @@ public class OsuFile implements Comparable { } /** - * Compares two OsuFile objects first by overall difficulty, then by total objects. + * Compares two Beatmap objects first by overall difficulty, then by total objects. */ @Override - public int compareTo(OsuFile that) { + public int compareTo(Beatmap that) { int cmp = Float.compare(this.overallDifficulty, that.overallDifficulty); if (cmp == 0) cmp = Integer.compare( diff --git a/src/itdelatrisu/opsu/OsuGroupList.java b/src/itdelatrisu/opsu/beatmap/BeatmapSetList.java similarity index 75% rename from src/itdelatrisu/opsu/OsuGroupList.java rename to src/itdelatrisu/opsu/beatmap/BeatmapSetList.java index bbfe4a3f..ad54c4db 100644 --- a/src/itdelatrisu/opsu/OsuGroupList.java +++ b/src/itdelatrisu/opsu/beatmap/BeatmapSetList.java @@ -16,10 +16,13 @@ * along with opsu!. If not, see . */ -package itdelatrisu.opsu; +package itdelatrisu.opsu.beatmap; +import itdelatrisu.opsu.ErrorHandler; +import itdelatrisu.opsu.SongSort; +import itdelatrisu.opsu.Utils; import itdelatrisu.opsu.audio.MusicController; -import itdelatrisu.opsu.db.OsuDB; +import itdelatrisu.opsu.db.BeatmapDB; import java.io.File; import java.io.IOException; @@ -35,9 +38,9 @@ import java.util.regex.Pattern; /** * Indexed, expanding, doubly-linked list data type for song groups. */ -public class OsuGroupList { - /** Song group structure (each group contains of an ArrayList of OsuFiles). */ - private static OsuGroupList list; +public class BeatmapSetList { + /** Song group structure (each group contains a list of beatmaps). */ + private static BeatmapSetList list; /** Search pattern for conditional expressions. */ private static final Pattern SEARCH_CONDITION_PATTERN = Pattern.compile( @@ -45,13 +48,13 @@ public class OsuGroupList { ); /** List containing all parsed nodes. */ - private ArrayList parsedNodes; + private ArrayList parsedNodes; - /** Total number of beatmaps (i.e. OsuFile objects). */ + /** Total number of beatmaps (i.e. Beatmap objects). */ private int mapCount = 0; /** Current list of nodes (subset of parsedNodes, used for searches). */ - private ArrayList nodes; + private ArrayList nodes; /** Set of all beatmap set IDs for the parsed beatmaps. */ private HashSet MSIDdb; @@ -60,7 +63,7 @@ public class OsuGroupList { private int expandedIndex; /** Start and end nodes of expanded group. */ - private OsuGroupNode expandedStartNode, expandedEndNode; + private BeatmapSetNode expandedStartNode, expandedEndNode; /** The last search query. */ private String lastQuery; @@ -68,18 +71,18 @@ public class OsuGroupList { /** * Creates a new instance of this class (overwriting any previous instance). */ - public static void create() { list = new OsuGroupList(); } + public static void create() { list = new BeatmapSetList(); } /** * Returns the single instance of this class. */ - public static OsuGroupList get() { return list; } + public static BeatmapSetList get() { return list; } /** * Constructor. */ - private OsuGroupList() { - parsedNodes = new ArrayList(); + private BeatmapSetList() { + parsedNodes = new ArrayList(); MSIDdb = new HashSet(); reset(); } @@ -102,16 +105,16 @@ public class OsuGroupList { /** * Adds a song group. - * @param osuFiles the list of OsuFile objects in the group - * @return the new OsuGroupNode + * @param beatmaps the list of beatmaps in the group + * @return the new BeatmapSetNode */ - public OsuGroupNode addSongGroup(ArrayList osuFiles) { - OsuGroupNode node = new OsuGroupNode(osuFiles); + public BeatmapSetNode addSongGroup(ArrayList beatmaps) { + BeatmapSetNode node = new BeatmapSetNode(beatmaps); parsedNodes.add(node); - mapCount += osuFiles.size(); + mapCount += beatmaps.size(); // add beatmap set ID to set - int msid = osuFiles.get(0).beatmapSetID; + int msid = beatmaps.get(0).beatmapSetID; if (msid > 0) MSIDdb.add(msid); @@ -124,13 +127,13 @@ public class OsuGroupList { * @param node the node containing the song group to delete * @return true if the song group was deleted, false otherwise */ - public boolean deleteSongGroup(OsuGroupNode node) { + public boolean deleteSongGroup(BeatmapSetNode node) { if (node == null) return false; // re-link base nodes int index = node.index; - OsuGroupNode ePrev = getBaseNode(index - 1), eCur = getBaseNode(index), eNext = getBaseNode(index + 1); + BeatmapSetNode ePrev = getBaseNode(index - 1), eCur = getBaseNode(index), eNext = getBaseNode(index + 1); if (ePrev != null) { if (ePrev.index == expandedIndex) expandedEndNode.next = eNext; @@ -149,12 +152,12 @@ public class OsuGroupList { } // remove all node references - OsuFile osu = node.osuFiles.get(0); + Beatmap beatmap = node.beatmaps.get(0); nodes.remove(index); parsedNodes.remove(eCur); - mapCount -= node.osuFiles.size(); - if (osu.beatmapSetID > 0) - MSIDdb.remove(osu.beatmapSetID); + mapCount -= node.beatmaps.size(); + if (beatmap.beatmapSetID > 0) + MSIDdb.remove(beatmap.beatmapSetID); // reset indices for (int i = index, size = size(); i < size; i++) @@ -164,25 +167,25 @@ public class OsuGroupList { expandedStartNode = expandedEndNode = null; } else if (expandedIndex > index) { expandedIndex--; - OsuGroupNode expandedNode = expandedStartNode; - for (int i = 0, size = expandedNode.osuFiles.size(); + BeatmapSetNode expandedNode = expandedStartNode; + for (int i = 0, size = expandedNode.beatmaps.size(); i < size && expandedNode != null; i++, expandedNode = expandedNode.next) expandedNode.index = expandedIndex; } // stop playing the track - File dir = osu.getFile().getParentFile(); + File dir = beatmap.getFile().getParentFile(); if (MusicController.trackExists() || MusicController.isTrackLoading()) { - File audioFile = MusicController.getOsuFile().audioFilename; - if (audioFile != null && audioFile.equals(osu.audioFilename)) { + File audioFile = MusicController.getBeatmap().audioFilename; + if (audioFile != null && audioFile.equals(beatmap.audioFilename)) { MusicController.reset(); System.gc(); // TODO: why can't files be deleted without calling this? } } // remove entry from cache - OsuDB.delete(dir.getName()); + BeatmapDB.delete(dir.getName()); // delete the associated directory try { @@ -200,26 +203,26 @@ public class OsuGroupList { * beatmap directory will be deleted altogether. * @param node the node containing the song group to delete (expanded only) * @return true if the song or song group was deleted, false otherwise - * @see #deleteSongGroup(OsuGroupNode) + * @see #deleteSongGroup(BeatmapSetNode) */ - public boolean deleteSong(OsuGroupNode node) { - if (node == null || node.osuFileIndex == -1 || node.index != expandedIndex) + public boolean deleteSong(BeatmapSetNode node) { + if (node == null || node.beatmapIndex == -1 || node.index != expandedIndex) return false; // last song in group? - int size = node.osuFiles.size(); - if (node.osuFiles.size() == 1) + int size = node.beatmaps.size(); + if (node.beatmaps.size() == 1) return deleteSongGroup(node); // reset indices - OsuGroupNode expandedNode = node.next; - for (int i = node.osuFileIndex + 1; + BeatmapSetNode expandedNode = node.next; + for (int i = node.beatmapIndex + 1; i < size && expandedNode != null && expandedNode.index == node.index; i++, expandedNode = expandedNode.next) - expandedNode.osuFileIndex--; + expandedNode.beatmapIndex--; // remove song reference - OsuFile osu = node.osuFiles.remove(node.osuFileIndex); + Beatmap beatmap = node.beatmaps.remove(node.beatmapIndex); mapCount--; // re-link nodes @@ -229,8 +232,8 @@ public class OsuGroupList { node.next.prev = node.prev; // remove entry from cache - File file = osu.getFile(); - OsuDB.delete(file.getParentFile().getName(), file.getName()); + File file = beatmap.getFile(); + BeatmapDB.delete(file.getParentFile().getName(), file.getName()); // delete the associated file try { @@ -243,7 +246,7 @@ public class OsuGroupList { } /** - * Returns the total number of parsed maps (i.e. OsuFile objects). + * Returns the total number of parsed maps (i.e. Beatmap objects). */ public int getMapCount() { return mapCount; } @@ -253,10 +256,10 @@ public class OsuGroupList { public int getMapSetCount() { return parsedNodes.size(); } /** - * Returns the OsuGroupNode at an index, disregarding expansions. + * Returns the BeatmapSetNode at an index, disregarding expansions. * @param index the node index */ - public OsuGroupNode getBaseNode(int index) { + public BeatmapSetNode getBaseNode(int index) { if (index < 0 || index >= size()) return null; @@ -266,20 +269,20 @@ public class OsuGroupList { /** * Returns a random base node. */ - public OsuGroupNode getRandomNode() { - OsuGroupNode node = getBaseNode((int) (Math.random() * size())); + public BeatmapSetNode getRandomNode() { + BeatmapSetNode node = getBaseNode((int) (Math.random() * size())); if (node != null && node.index == expandedIndex) // don't choose an expanded group node node = node.next; return node; } /** - * Returns the OsuGroupNode a given number of positions forward or backwards. + * Returns the BeatmapSetNode a given number of positions forward or backwards. * @param node the starting node * @param shift the number of nodes to shift forward (+) or backward (-). */ - public OsuGroupNode getNode(OsuGroupNode node, int shift) { - OsuGroupNode startNode = node; + public BeatmapSetNode getNode(BeatmapSetNode node, int shift) { + BeatmapSetNode startNode = node; if (shift > 0) { for (int i = 0; i < shift && startNode != null; i++) startNode = startNode.next; @@ -296,28 +299,28 @@ public class OsuGroupList { public int getExpandedIndex() { return expandedIndex; } /** - * Expands the node at an index by inserting a new node for each OsuFile + * Expands the node at an index by inserting a new node for each Beatmap * in that node and hiding the group node. * @return the first of the newly-inserted nodes */ - public OsuGroupNode expand(int index) { + public BeatmapSetNode expand(int index) { // undo the previous expansion unexpand(); - OsuGroupNode node = getBaseNode(index); + BeatmapSetNode node = getBaseNode(index); if (node == null) return null; expandedStartNode = expandedEndNode = null; // create new nodes - ArrayList osuFiles = node.osuFiles; - OsuGroupNode prevNode = node.prev; - OsuGroupNode nextNode = node.next; - for (int i = 0, size = node.osuFiles.size(); i < size; i++) { - OsuGroupNode newNode = new OsuGroupNode(osuFiles); + ArrayList beatmaps = node.beatmaps; + BeatmapSetNode prevNode = node.prev; + BeatmapSetNode nextNode = node.next; + for (int i = 0, size = node.beatmaps.size(); i < size; i++) { + BeatmapSetNode newNode = new BeatmapSetNode(beatmaps); newNode.index = index; - newNode.osuFileIndex = i; + newNode.beatmapIndex = i; newNode.prev = node; // unlink the group node @@ -349,7 +352,7 @@ public class OsuGroupList { return; // recreate surrounding links - OsuGroupNode + BeatmapSetNode ePrev = getBaseNode(expandedIndex - 1), eCur = getBaseNode(expandedIndex), eNext = getBaseNode(expandedIndex + 1); @@ -379,11 +382,11 @@ public class OsuGroupList { expandedStartNode = expandedEndNode = null; // create links - OsuGroupNode lastNode = nodes.get(0); + BeatmapSetNode lastNode = nodes.get(0); lastNode.index = 0; lastNode.prev = null; for (int i = 1, size = size(); i < size; i++) { - OsuGroupNode node = nodes.get(i); + BeatmapSetNode node = nodes.get(i); lastNode.next = node; node.index = i; node.prev = lastNode; @@ -433,20 +436,20 @@ public class OsuGroupList { } // build an initial list from first search term - nodes = new ArrayList(); + nodes = new ArrayList(); if (terms.isEmpty()) { // conditional term String type = condType.remove(); String operator = condOperator.remove(); float value = condValue.remove(); - for (OsuGroupNode node : parsedNodes) { + for (BeatmapSetNode node : parsedNodes) { if (node.matches(type, operator, value)) nodes.add(node); } } else { // normal term String term = terms.remove(); - for (OsuGroupNode node : parsedNodes) { + for (BeatmapSetNode node : parsedNodes) { if (node.matches(term)) nodes.add(node); } @@ -460,9 +463,9 @@ public class OsuGroupList { String term = terms.remove(); // remove nodes from list if they don't match all terms - Iterator nodeIter = nodes.iterator(); + Iterator nodeIter = nodes.iterator(); while (nodeIter.hasNext()) { - OsuGroupNode node = nodeIter.next(); + BeatmapSetNode node = nodeIter.next(); if (!node.matches(term)) nodeIter.remove(); } @@ -478,9 +481,9 @@ public class OsuGroupList { float value = condValue.remove(); // remove nodes from list if they don't match all terms - Iterator nodeIter = nodes.iterator(); + Iterator nodeIter = nodes.iterator(); while (nodeIter.hasNext()) { - OsuGroupNode node = nodeIter.next(); + BeatmapSetNode node = nodeIter.next(); if (!node.matches(type, operator, value)) nodeIter.remove(); } diff --git a/src/itdelatrisu/opsu/OsuGroupNode.java b/src/itdelatrisu/opsu/beatmap/BeatmapSetNode.java similarity index 54% rename from src/itdelatrisu/opsu/OsuGroupNode.java rename to src/itdelatrisu/opsu/beatmap/BeatmapSetNode.java index 721f58d8..fb48ad73 100644 --- a/src/itdelatrisu/opsu/OsuGroupNode.java +++ b/src/itdelatrisu/opsu/beatmap/BeatmapSetNode.java @@ -16,9 +16,13 @@ * along with opsu!. If not, see . */ -package itdelatrisu.opsu; +package itdelatrisu.opsu.beatmap; import itdelatrisu.opsu.GameData.Grade; +import itdelatrisu.opsu.GameImage; +import itdelatrisu.opsu.GameMod; +import itdelatrisu.opsu.Options; +import itdelatrisu.opsu.Utils; import java.util.ArrayList; import java.util.concurrent.TimeUnit; @@ -27,27 +31,27 @@ import org.newdawn.slick.Color; import org.newdawn.slick.Image; /** - * Node in an OsuGroupList representing a group of OsuFile objects. + * Node in an BeatmapSetList representing a group of beatmaps. */ -public class OsuGroupNode { - /** List of associated OsuFile objects. */ - public ArrayList osuFiles; +public class BeatmapSetNode { + /** List of associated beatmaps. */ + public ArrayList beatmaps; - /** Index of this OsuGroupNode. */ + /** Index of this node. */ public int index = 0; - /** Index of selected osuFile (-1 if not focused). */ - public int osuFileIndex = -1; + /** Index of the selected beatmap (-1 if not focused). */ + public int beatmapIndex = -1; - /** Links to other OsuGroupNode objects. */ - public OsuGroupNode prev, next; + /** Links to other nodes. */ + public BeatmapSetNode prev, next; /** * Constructor. - * @param osuFiles the OsuFile objects in this group + * @param beatmaps the beatmaps in this group */ - public OsuGroupNode(ArrayList osuFiles) { - this.osuFiles = osuFiles; + public BeatmapSetNode(ArrayList beatmaps) { + this.beatmaps = beatmaps; } /** @@ -59,8 +63,8 @@ public class OsuGroupNode { */ public void draw(float x, float y, Grade grade, boolean focus) { Image bg = GameImage.MENU_BUTTON_BG.getImage(); - boolean expanded = (osuFileIndex > -1); - OsuFile osu; + boolean expanded = (beatmapIndex > -1); + Beatmap beatmap; bg.setAlpha(0.9f); Color bgColor; Color textColor = Color.lightGray; @@ -73,10 +77,10 @@ public class OsuGroupNode { textColor = Color.white; } else bgColor = Utils.COLOR_BLUE_BUTTON; - osu = osuFiles.get(osuFileIndex); + beatmap = beatmaps.get(beatmapIndex); } else { bgColor = Utils.COLOR_ORANGE_BUTTON; - osu = osuFiles.get(0); + beatmap = beatmaps.get(0); } bg.draw(x, y, bgColor); @@ -92,15 +96,15 @@ public class OsuGroupNode { // draw text if (Options.useUnicodeMetadata()) { // load glyphs - Utils.loadGlyphs(Utils.FONT_MEDIUM, osu.titleUnicode, null); - Utils.loadGlyphs(Utils.FONT_DEFAULT, null, osu.artistUnicode); + Utils.loadGlyphs(Utils.FONT_MEDIUM, beatmap.titleUnicode, null); + Utils.loadGlyphs(Utils.FONT_DEFAULT, null, beatmap.artistUnicode); } - Utils.FONT_MEDIUM.drawString(cx, cy, osu.getTitle(), textColor); + Utils.FONT_MEDIUM.drawString(cx, cy, beatmap.getTitle(), textColor); Utils.FONT_DEFAULT.drawString(cx, cy + Utils.FONT_MEDIUM.getLineHeight() - 2, - String.format("%s // %s", osu.getArtist(), osu.creator), textColor); - if (expanded || osuFiles.size() == 1) + String.format("%s // %s", beatmap.getArtist(), beatmap.creator), textColor); + if (expanded || beatmaps.size() == 1) Utils.FONT_BOLD.drawString(cx, cy + Utils.FONT_MEDIUM.getLineHeight() + Utils.FONT_DEFAULT.getLineHeight() - 4, - osu.version, textColor); + beatmap.version, textColor); } /** @@ -114,45 +118,45 @@ public class OsuGroupNode { * */ public String[] getInfo() { - if (osuFileIndex < 0) + if (beatmapIndex < 0) return null; - OsuFile osu = osuFiles.get(osuFileIndex); + Beatmap beatmap = beatmaps.get(beatmapIndex); float speedModifier = GameMod.getSpeedMultiplier(); - long endTime = (long) (osu.endTime / speedModifier); - int bpmMin = (int) (osu.bpmMin * speedModifier); - int bpmMax = (int) (osu.bpmMax * speedModifier); + long endTime = (long) (beatmap.endTime / speedModifier); + int bpmMin = (int) (beatmap.bpmMin * speedModifier); + int bpmMax = (int) (beatmap.bpmMax * speedModifier); float multiplier = GameMod.getDifficultyMultiplier(); String[] info = new String[5]; - info[0] = osu.toString(); - info[1] = String.format("Mapped by %s", osu.creator); + info[0] = beatmap.toString(); + info[1] = String.format("Mapped by %s", beatmap.creator); info[2] = String.format("Length: %d:%02d BPM: %s Objects: %d", TimeUnit.MILLISECONDS.toMinutes(endTime), TimeUnit.MILLISECONDS.toSeconds(endTime) - TimeUnit.MINUTES.toSeconds(TimeUnit.MILLISECONDS.toMinutes(endTime)), (bpmMax <= 0) ? "--" : ((bpmMin == bpmMax) ? bpmMin : String.format("%d-%d", bpmMin, bpmMax)), - (osu.hitObjectCircle + osu.hitObjectSlider + osu.hitObjectSpinner)); + (beatmap.hitObjectCircle + beatmap.hitObjectSlider + beatmap.hitObjectSpinner)); info[3] = String.format("Circles: %d Sliders: %d Spinners: %d", - osu.hitObjectCircle, osu.hitObjectSlider, osu.hitObjectSpinner); + beatmap.hitObjectCircle, beatmap.hitObjectSlider, beatmap.hitObjectSpinner); info[4] = String.format("CS:%.1f HP:%.1f AR:%.1f OD:%.1f", - Math.min(osu.circleSize * multiplier, 10f), - Math.min(osu.HPDrainRate * multiplier, 10f), - Math.min(osu.approachRate * multiplier, 10f), - Math.min(osu.overallDifficulty * multiplier, 10f)); + Math.min(beatmap.circleSize * multiplier, 10f), + Math.min(beatmap.HPDrainRate * multiplier, 10f), + Math.min(beatmap.approachRate * multiplier, 10f), + Math.min(beatmap.overallDifficulty * multiplier, 10f)); return info; } /** - * Returns a formatted string for the OsuFile at osuFileIndex: - * "Artist - Title [Version]" (version omitted if osuFileIndex is invalid) + * Returns a formatted string for the beatmap at {@code beatmapIndex}: + * "Artist - Title [Version]" (version omitted if {@code beatmapIndex} is invalid) * @see java.lang.Object#toString() */ @Override public String toString() { - if (osuFileIndex == -1) - return String.format("%s - %s", osuFiles.get(0).getArtist(), osuFiles.get(0).getTitle()); + if (beatmapIndex == -1) + return String.format("%s - %s", beatmaps.get(0).getArtist(), beatmaps.get(0).getTitle()); else - return osuFiles.get(osuFileIndex).toString(); + return beatmaps.get(beatmapIndex).toString(); } /** @@ -161,24 +165,24 @@ public class OsuGroupNode { * @return true if title, artist, creator, source, version, or tag matches query */ public boolean matches(String query) { - OsuFile osu = osuFiles.get(0); + Beatmap beatmap = beatmaps.get(0); - // search: title, artist, creator, source, version, tags (first OsuFile) - if (osu.title.toLowerCase().contains(query) || - osu.titleUnicode.toLowerCase().contains(query) || - osu.artist.toLowerCase().contains(query) || - osu.artistUnicode.toLowerCase().contains(query) || - osu.creator.toLowerCase().contains(query) || - osu.source.toLowerCase().contains(query) || - osu.version.toLowerCase().contains(query) || - osu.tags.contains(query)) + // search: title, artist, creator, source, version, tags (first beatmap) + if (beatmap.title.toLowerCase().contains(query) || + beatmap.titleUnicode.toLowerCase().contains(query) || + beatmap.artist.toLowerCase().contains(query) || + beatmap.artistUnicode.toLowerCase().contains(query) || + beatmap.creator.toLowerCase().contains(query) || + beatmap.source.toLowerCase().contains(query) || + beatmap.version.toLowerCase().contains(query) || + beatmap.tags.contains(query)) return true; - // search: version, tags (remaining OsuFiles) - for (int i = 1; i < osuFiles.size(); i++) { - osu = osuFiles.get(i); - if (osu.version.toLowerCase().contains(query) || - osu.tags.contains(query)) + // search: version, tags (remaining beatmaps) + for (int i = 1; i < beatmaps.size(); i++) { + beatmap = beatmaps.get(i); + if (beatmap.version.toLowerCase().contains(query) || + beatmap.tags.contains(query)) return true; } @@ -193,16 +197,16 @@ public class OsuGroupNode { * @return true if the condition is met */ public boolean matches(String type, String operator, float value) { - for (OsuFile osu : osuFiles) { + for (Beatmap beatmap : beatmaps) { // get value - float osuValue; + float v; switch (type) { - case "ar": osuValue = osu.approachRate; break; - case "cs": osuValue = osu.circleSize; break; - case "od": osuValue = osu.overallDifficulty; break; - case "hp": osuValue = osu.HPDrainRate; break; - case "bpm": osuValue = osu.bpmMax; break; - case "length": osuValue = osu.endTime / 1000; break; + case "ar": v = beatmap.approachRate; break; + case "cs": v = beatmap.circleSize; break; + case "od": v = beatmap.overallDifficulty; break; + case "hp": v = beatmap.HPDrainRate; break; + case "bpm": v = beatmap.bpmMax; break; + case "length": v = beatmap.endTime / 1000; break; default: return false; } @@ -210,11 +214,11 @@ public class OsuGroupNode { boolean met; switch (operator) { case "=": - case "==": met = (osuValue == value); break; - case ">": met = (osuValue > value); break; - case ">=": met = (osuValue >= value); break; - case "<": met = (osuValue < value); break; - case "<=": met = (osuValue <= value); break; + case "==": met = (v == value); break; + case ">": met = (v > value); break; + case ">=": met = (v >= value); break; + case "<": met = (v < value); break; + case "<=": met = (v <= value); break; default: return false; } diff --git a/src/itdelatrisu/opsu/OsuHitObject.java b/src/itdelatrisu/opsu/beatmap/OsuHitObject.java similarity index 99% rename from src/itdelatrisu/opsu/OsuHitObject.java rename to src/itdelatrisu/opsu/beatmap/OsuHitObject.java index e6d75c04..a05bd7ae 100644 --- a/src/itdelatrisu/opsu/OsuHitObject.java +++ b/src/itdelatrisu/opsu/beatmap/OsuHitObject.java @@ -16,13 +16,15 @@ * along with opsu!. If not, see . */ -package itdelatrisu.opsu; +package itdelatrisu.opsu.beatmap; + +import itdelatrisu.opsu.GameMod; import java.text.DecimalFormat; import java.text.NumberFormat; /** - * Data type representing a hit object. + * Data type representing a parsed hit object. */ public class OsuHitObject { /** Hit object types (bits). */ diff --git a/src/itdelatrisu/opsu/TimingPoint.java b/src/itdelatrisu/opsu/beatmap/TimingPoint.java similarity index 99% rename from src/itdelatrisu/opsu/TimingPoint.java rename to src/itdelatrisu/opsu/beatmap/TimingPoint.java index bce03408..369fc5be 100644 --- a/src/itdelatrisu/opsu/TimingPoint.java +++ b/src/itdelatrisu/opsu/beatmap/TimingPoint.java @@ -16,7 +16,7 @@ * along with opsu!. If not, see . */ -package itdelatrisu.opsu; +package itdelatrisu.opsu.beatmap; import org.newdawn.slick.util.Log; diff --git a/src/itdelatrisu/opsu/db/OsuDB.java b/src/itdelatrisu/opsu/db/BeatmapDB.java similarity index 68% rename from src/itdelatrisu/opsu/db/OsuDB.java rename to src/itdelatrisu/opsu/db/BeatmapDB.java index c2b76e83..a9282419 100644 --- a/src/itdelatrisu/opsu/db/OsuDB.java +++ b/src/itdelatrisu/opsu/db/BeatmapDB.java @@ -20,8 +20,8 @@ package itdelatrisu.opsu.db; import itdelatrisu.opsu.ErrorHandler; import itdelatrisu.opsu.Options; -import itdelatrisu.opsu.OsuFile; import itdelatrisu.opsu.OsuParser; +import itdelatrisu.opsu.beatmap.Beatmap; import java.io.File; import java.sql.Connection; @@ -38,7 +38,7 @@ import org.newdawn.slick.util.Log; /** * Handles connections and queries with the cached beatmap database. */ -public class OsuDB { +public class BeatmapDB { /** * Current database version. * This value should be changed whenever the database format changes. @@ -51,7 +51,7 @@ public class OsuDB { /** Minimum batch size to invoke batch insertion. */ private static final int INSERT_BATCH_MIN = 100; - /** OsuFile loading flags. */ + /** Beatmap loading flags. */ public static final int LOAD_NONARRAY = 1, LOAD_ARRAY = 2, LOAD_ALL = 3; /** Database connection. */ @@ -64,14 +64,14 @@ public class OsuDB { private static int cacheSize = -1; // This class should not be instantiated. - private OsuDB() {} + private BeatmapDB() {} /** * Initializes the database connection. */ public static void init() { // create a database connection - connection = DBController.createConnection(Options.OSU_DB.getPath()); + connection = DBController.createConnection(Options.BEATMAP_DB.getPath()); if (connection == null) return; @@ -216,15 +216,15 @@ public class OsuDB { } /** - * Adds the OsuFile to the database. - * @param osu the OsuFile object + * Adds the beatmap to the database. + * @param beatmap the beatmap */ - public static void insert(OsuFile osu) { + public static void insert(Beatmap beatmap) { if (connection == null) return; try { - setStatementFields(insertStmt, osu); + setStatementFields(insertStmt, beatmap); cacheSize += insertStmt.executeUpdate(); updateCacheSize(); } catch (SQLException e) { @@ -233,10 +233,10 @@ public class OsuDB { } /** - * Adds the OsuFiles to the database in a batch. - * @param batch a list of OsuFile objects + * Adds the beatmaps to the database in a batch. + * @param batch a list of beatmaps */ - public static void insert(List batch) { + public static void insert(List batch) { if (connection == null) return; @@ -253,11 +253,11 @@ public class OsuDB { } // batch insert - for (OsuFile osu : batch) { + for (Beatmap beatmap : batch) { try { - setStatementFields(insertStmt, osu); + setStatementFields(insertStmt, beatmap); } catch (SQLException e) { - Log.error(String.format("Failed to insert map '%s' into database.", osu.getFile().getPath()), e); + Log.error(String.format("Failed to insert map '%s' into database.", beatmap.getFile().getPath()), e); continue; } insertStmt.addBatch(); @@ -286,53 +286,53 @@ public class OsuDB { } /** - * Sets all statement fields using a given OsuFile object. + * Sets all statement fields using a given beatmap. * @param stmt the statement to set fields for - * @param osu the OsuFile + * @param beatmap the beatmap * @throws SQLException */ - private static void setStatementFields(PreparedStatement stmt, OsuFile osu) + private static void setStatementFields(PreparedStatement stmt, Beatmap beatmap) throws SQLException { try { - stmt.setString(1, osu.getFile().getParentFile().getName()); - stmt.setString(2, osu.getFile().getName()); - stmt.setLong(3, osu.getFile().lastModified()); - stmt.setInt(4, osu.beatmapID); - stmt.setInt(5, osu.beatmapSetID); - stmt.setString(6, osu.title); - stmt.setString(7, osu.titleUnicode); - stmt.setString(8, osu.artist); - stmt.setString(9, osu.artistUnicode); - stmt.setString(10, osu.creator); - stmt.setString(11, osu.version); - stmt.setString(12, osu.source); - stmt.setString(13, osu.tags); - stmt.setInt(14, osu.hitObjectCircle); - stmt.setInt(15, osu.hitObjectSlider); - stmt.setInt(16, osu.hitObjectSpinner); - stmt.setFloat(17, osu.HPDrainRate); - stmt.setFloat(18, osu.circleSize); - stmt.setFloat(19, osu.overallDifficulty); - stmt.setFloat(20, osu.approachRate); - stmt.setFloat(21, osu.sliderMultiplier); - stmt.setFloat(22, osu.sliderTickRate); - stmt.setInt(23, osu.bpmMin); - stmt.setInt(24, osu.bpmMax); - stmt.setInt(25, osu.endTime); - stmt.setString(26, osu.audioFilename.getName()); - stmt.setInt(27, osu.audioLeadIn); - stmt.setInt(28, osu.previewTime); - stmt.setByte(29, osu.countdown); - stmt.setString(30, osu.sampleSet); - stmt.setFloat(31, osu.stackLeniency); - stmt.setByte(32, osu.mode); - stmt.setBoolean(33, osu.letterboxInBreaks); - stmt.setBoolean(34, osu.widescreenStoryboard); - stmt.setBoolean(35, osu.epilepsyWarning); - stmt.setString(36, osu.bg); - stmt.setString(37, osu.timingPointsToString()); - stmt.setString(38, osu.breaksToString()); - stmt.setString(39, osu.comboToString()); + stmt.setString(1, beatmap.getFile().getParentFile().getName()); + stmt.setString(2, beatmap.getFile().getName()); + stmt.setLong(3, beatmap.getFile().lastModified()); + stmt.setInt(4, beatmap.beatmapID); + stmt.setInt(5, beatmap.beatmapSetID); + stmt.setString(6, beatmap.title); + stmt.setString(7, beatmap.titleUnicode); + stmt.setString(8, beatmap.artist); + stmt.setString(9, beatmap.artistUnicode); + stmt.setString(10, beatmap.creator); + stmt.setString(11, beatmap.version); + stmt.setString(12, beatmap.source); + stmt.setString(13, beatmap.tags); + stmt.setInt(14, beatmap.hitObjectCircle); + stmt.setInt(15, beatmap.hitObjectSlider); + stmt.setInt(16, beatmap.hitObjectSpinner); + stmt.setFloat(17, beatmap.HPDrainRate); + stmt.setFloat(18, beatmap.circleSize); + stmt.setFloat(19, beatmap.overallDifficulty); + stmt.setFloat(20, beatmap.approachRate); + stmt.setFloat(21, beatmap.sliderMultiplier); + stmt.setFloat(22, beatmap.sliderTickRate); + stmt.setInt(23, beatmap.bpmMin); + stmt.setInt(24, beatmap.bpmMax); + stmt.setInt(25, beatmap.endTime); + stmt.setString(26, beatmap.audioFilename.getName()); + stmt.setInt(27, beatmap.audioLeadIn); + stmt.setInt(28, beatmap.previewTime); + stmt.setByte(29, beatmap.countdown); + stmt.setString(30, beatmap.sampleSet); + stmt.setFloat(31, beatmap.stackLeniency); + stmt.setByte(32, beatmap.mode); + stmt.setBoolean(33, beatmap.letterboxInBreaks); + stmt.setBoolean(34, beatmap.widescreenStoryboard); + stmt.setBoolean(35, beatmap.epilepsyWarning); + stmt.setString(36, beatmap.bg); + stmt.setString(37, beatmap.timingPointsToString()); + stmt.setString(38, beatmap.breaksToString()); + stmt.setString(39, beatmap.comboToString()); } catch (SQLException e) { throw e; } catch (Exception e) { @@ -341,80 +341,80 @@ public class OsuDB { } /** - * Loads OsuFile fields from the database. - * @param osu the OsuFile object + * Loads beatmap fields from the database. + * @param beatmap the beatmap * @param flag whether to load all fields (LOAD_ALL), non-array * fields (LOAD_NONARRAY), or array fields (LOAD_ARRAY) */ - public static void load(OsuFile osu, int flag) { + public static void load(Beatmap beatmap, int flag) { if (connection == null) return; try { - selectStmt.setString(1, osu.getFile().getParentFile().getName()); - selectStmt.setString(2, osu.getFile().getName()); + selectStmt.setString(1, beatmap.getFile().getParentFile().getName()); + selectStmt.setString(2, beatmap.getFile().getName()); ResultSet rs = selectStmt.executeQuery(); if (rs.next()) { if ((flag & LOAD_NONARRAY) > 0) - setOsuFileFields(rs, osu); + setBeatmapFields(rs, beatmap); if ((flag & LOAD_ARRAY) > 0) - setOsuFileArrayFields(rs, osu); + setBeatmapArrayFields(rs, beatmap); } rs.close(); } catch (SQLException e) { - ErrorHandler.error("Failed to load OsuFile from database.", e, true); + ErrorHandler.error("Failed to load Beatmap from database.", e, true); } } /** - * Loads OsuFile fields from the database in a batch. - * @param batch a list of OsuFile objects + * Loads Beatmap fields from the database in a batch. + * @param batch a list of beatmaps * @param flag whether to load all fields (LOAD_ALL), non-array * fields (LOAD_NONARRAY), or array fields (LOAD_ARRAY) */ - public static void load(List batch, int flag) { + public static void load(List batch, int flag) { if (connection == null) return; // batch size too small int size = batch.size(); if (size < cacheSize * LOAD_BATCH_MIN_RATIO) { - for (OsuFile osu : batch) - load(osu, flag); + for (Beatmap beatmap : batch) + load(beatmap, flag); return; } try (Statement stmt = connection.createStatement()) { // create map - HashMap> map = new HashMap>(); - for (OsuFile osu : batch) { - String parent = osu.getFile().getParentFile().getName(); - String name = osu.getFile().getName(); - HashMap m = map.get(parent); + HashMap> map = new HashMap>(); + for (Beatmap beatmap : batch) { + String parent = beatmap.getFile().getParentFile().getName(); + String name = beatmap.getFile().getName(); + HashMap m = map.get(parent); if (m == null) { - m = new HashMap(); + m = new HashMap(); map.put(parent, m); } - m.put(name, osu); + m.put(name, beatmap); } - // iterate through database to load OsuFiles + // iterate through database to load beatmaps int count = 0; stmt.setFetchSize(100); String sql = "SELECT * FROM beatmaps"; ResultSet rs = stmt.executeQuery(sql); while (rs.next()) { String parent = rs.getString(1); - HashMap m = map.get(parent); + HashMap m = map.get(parent); if (m != null) { String name = rs.getString(2); - OsuFile osu = m.get(name); - if (osu != null) { + Beatmap beatmap = m.get(name); + if (beatmap != null) { try { if ((flag & LOAD_NONARRAY) > 0) - setOsuFileFields(rs, osu); + setBeatmapFields(rs, beatmap); if ((flag & LOAD_ARRAY) > 0) - setOsuFileArrayFields(rs, osu); + setBeatmapArrayFields(rs, beatmap); } catch (SQLException e) { Log.error(String.format("Failed to load map '%s/%s' from database.", parent, name), e); } @@ -425,51 +425,51 @@ public class OsuDB { } rs.close(); } catch (SQLException e) { - ErrorHandler.error("Failed to load OsuFiles from database.", e, true); + ErrorHandler.error("Failed to load beatmaps from database.", e, true); } } /** - * Sets all OsuFile non-array fields using a given result set. + * Sets all beatmap non-array fields using a given result set. * @param rs the result set containing the fields - * @param osu the OsuFile + * @param beatmap the beatmap * @throws SQLException */ - private static void setOsuFileFields(ResultSet rs, OsuFile osu) throws SQLException { + private static void setBeatmapFields(ResultSet rs, Beatmap beatmap) throws SQLException { try { - osu.beatmapID = rs.getInt(4); - osu.beatmapSetID = rs.getInt(5); - osu.title = OsuParser.getDBString(rs.getString(6)); - osu.titleUnicode = OsuParser.getDBString(rs.getString(7)); - osu.artist = OsuParser.getDBString(rs.getString(8)); - osu.artistUnicode = OsuParser.getDBString(rs.getString(9)); - osu.creator = OsuParser.getDBString(rs.getString(10)); - osu.version = OsuParser.getDBString(rs.getString(11)); - osu.source = OsuParser.getDBString(rs.getString(12)); - osu.tags = OsuParser.getDBString(rs.getString(13)); - osu.hitObjectCircle = rs.getInt(14); - osu.hitObjectSlider = rs.getInt(15); - osu.hitObjectSpinner = rs.getInt(16); - osu.HPDrainRate = rs.getFloat(17); - osu.circleSize = rs.getFloat(18); - osu.overallDifficulty = rs.getFloat(19); - osu.approachRate = rs.getFloat(20); - osu.sliderMultiplier = rs.getFloat(21); - osu.sliderTickRate = rs.getFloat(22); - osu.bpmMin = rs.getInt(23); - osu.bpmMax = rs.getInt(24); - osu.endTime = rs.getInt(25); - osu.audioFilename = new File(osu.getFile().getParentFile(), OsuParser.getDBString(rs.getString(26))); - osu.audioLeadIn = rs.getInt(27); - osu.previewTime = rs.getInt(28); - osu.countdown = rs.getByte(29); - osu.sampleSet = OsuParser.getDBString(rs.getString(30)); - osu.stackLeniency = rs.getFloat(31); - osu.mode = rs.getByte(32); - osu.letterboxInBreaks = rs.getBoolean(33); - osu.widescreenStoryboard = rs.getBoolean(34); - osu.epilepsyWarning = rs.getBoolean(35); - osu.bg = OsuParser.getDBString(rs.getString(36)); + beatmap.beatmapID = rs.getInt(4); + beatmap.beatmapSetID = rs.getInt(5); + beatmap.title = OsuParser.getDBString(rs.getString(6)); + beatmap.titleUnicode = OsuParser.getDBString(rs.getString(7)); + beatmap.artist = OsuParser.getDBString(rs.getString(8)); + beatmap.artistUnicode = OsuParser.getDBString(rs.getString(9)); + beatmap.creator = OsuParser.getDBString(rs.getString(10)); + beatmap.version = OsuParser.getDBString(rs.getString(11)); + beatmap.source = OsuParser.getDBString(rs.getString(12)); + beatmap.tags = OsuParser.getDBString(rs.getString(13)); + beatmap.hitObjectCircle = rs.getInt(14); + beatmap.hitObjectSlider = rs.getInt(15); + beatmap.hitObjectSpinner = rs.getInt(16); + beatmap.HPDrainRate = rs.getFloat(17); + beatmap.circleSize = rs.getFloat(18); + beatmap.overallDifficulty = rs.getFloat(19); + beatmap.approachRate = rs.getFloat(20); + beatmap.sliderMultiplier = rs.getFloat(21); + beatmap.sliderTickRate = rs.getFloat(22); + beatmap.bpmMin = rs.getInt(23); + beatmap.bpmMax = rs.getInt(24); + beatmap.endTime = rs.getInt(25); + beatmap.audioFilename = new File(beatmap.getFile().getParentFile(), OsuParser.getDBString(rs.getString(26))); + beatmap.audioLeadIn = rs.getInt(27); + beatmap.previewTime = rs.getInt(28); + beatmap.countdown = rs.getByte(29); + beatmap.sampleSet = OsuParser.getDBString(rs.getString(30)); + beatmap.stackLeniency = rs.getFloat(31); + beatmap.mode = rs.getByte(32); + beatmap.letterboxInBreaks = rs.getBoolean(33); + beatmap.widescreenStoryboard = rs.getBoolean(34); + beatmap.epilepsyWarning = rs.getBoolean(35); + beatmap.bg = OsuParser.getDBString(rs.getString(36)); } catch (SQLException e) { throw e; } catch (Exception e) { @@ -478,16 +478,16 @@ public class OsuDB { } /** - * Sets all OsuFile array fields using a given result set. + * Sets all Beatmap array fields using a given result set. * @param rs the result set containing the fields - * @param osu the OsuFile + * @param beatmap the beatmap * @throws SQLException */ - private static void setOsuFileArrayFields(ResultSet rs, OsuFile osu) throws SQLException { + private static void setBeatmapArrayFields(ResultSet rs, Beatmap beatmap) throws SQLException { try { - osu.timingPointsFromString(rs.getString(37)); - osu.breaksFromString(rs.getString(38)); - osu.comboFromString(rs.getString(39)); + beatmap.timingPointsFromString(rs.getString(37)); + beatmap.breaksFromString(rs.getString(38)); + beatmap.comboFromString(rs.getString(39)); } catch (SQLException e) { throw e; } catch (Exception e) { diff --git a/src/itdelatrisu/opsu/db/DBController.java b/src/itdelatrisu/opsu/db/DBController.java index 05841b6c..aebd414b 100644 --- a/src/itdelatrisu/opsu/db/DBController.java +++ b/src/itdelatrisu/opsu/db/DBController.java @@ -43,7 +43,7 @@ public class DBController { } // initialize the databases - OsuDB.init(); + BeatmapDB.init(); ScoreDB.init(); } @@ -51,7 +51,7 @@ public class DBController { * Closes all database connections. */ public static void closeConnections() { - OsuDB.closeConnection(); + BeatmapDB.closeConnection(); ScoreDB.closeConnection(); } diff --git a/src/itdelatrisu/opsu/db/ScoreDB.java b/src/itdelatrisu/opsu/db/ScoreDB.java index 7744992d..5ac5c300 100644 --- a/src/itdelatrisu/opsu/db/ScoreDB.java +++ b/src/itdelatrisu/opsu/db/ScoreDB.java @@ -20,8 +20,8 @@ package itdelatrisu.opsu.db; import itdelatrisu.opsu.ErrorHandler; import itdelatrisu.opsu.Options; -import itdelatrisu.opsu.OsuFile; import itdelatrisu.opsu.ScoreData; +import itdelatrisu.opsu.beatmap.Beatmap; import java.sql.Connection; import java.sql.PreparedStatement; @@ -240,18 +240,18 @@ public class ScoreDB { /** * Deletes all the scores for the given beatmap from the database. - * @param osu the OsuFile object + * @param beatmap the beatmap */ - public static void deleteScore(OsuFile osu) { + public static void deleteScore(Beatmap beatmap) { if (connection == null) return; try { - deleteSongStmt.setInt(1, osu.beatmapID); - deleteSongStmt.setString(2, osu.title); - deleteSongStmt.setString(3, osu.artist); - deleteSongStmt.setString(4, osu.creator); - deleteSongStmt.setString(5, osu.version); + deleteSongStmt.setInt(1, beatmap.beatmapID); + deleteSongStmt.setString(2, beatmap.title); + deleteSongStmt.setString(3, beatmap.artist); + deleteSongStmt.setString(4, beatmap.creator); + deleteSongStmt.setString(5, beatmap.version); deleteSongStmt.executeUpdate(); } catch (SQLException e) { ErrorHandler.error("Failed to delete scores from database.", e, true); @@ -286,21 +286,21 @@ public class ScoreDB { } /** - * Retrieves the game scores for an OsuFile map. - * @param osu the OsuFile + * Retrieves the game scores for a beatmap. + * @param beatmap the beatmap * @return all scores for the beatmap, or null if any error occurred */ - public static ScoreData[] getMapScores(OsuFile osu) { + public static ScoreData[] getMapScores(Beatmap beatmap) { if (connection == null) return null; List list = new ArrayList(); try { - selectMapStmt.setInt(1, osu.beatmapID); - selectMapStmt.setString(2, osu.title); - selectMapStmt.setString(3, osu.artist); - selectMapStmt.setString(4, osu.creator); - selectMapStmt.setString(5, osu.version); + selectMapStmt.setInt(1, beatmap.beatmapID); + selectMapStmt.setString(2, beatmap.title); + selectMapStmt.setString(3, beatmap.artist); + selectMapStmt.setString(4, beatmap.creator); + selectMapStmt.setString(5, beatmap.version); ResultSet rs = selectMapStmt.executeQuery(); while (rs.next()) { ScoreData s = new ScoreData(rs); @@ -315,21 +315,21 @@ public class ScoreDB { } /** - * Retrieves the game scores for an OsuFile map set. - * @param osu the OsuFile + * Retrieves the game scores for a beatmap set. + * @param beatmap the beatmap * @return all scores for the beatmap set (Version, ScoreData[]), * or null if any error occurred */ - public static Map getMapSetScores(OsuFile osu) { + public static Map getMapSetScores(Beatmap beatmap) { if (connection == null) return null; Map map = new HashMap(); try { - selectMapSetStmt.setInt(1, osu.beatmapSetID); - selectMapSetStmt.setString(2, osu.title); - selectMapSetStmt.setString(3, osu.artist); - selectMapSetStmt.setString(4, osu.creator); + selectMapSetStmt.setInt(1, beatmap.beatmapSetID); + selectMapSetStmt.setString(2, beatmap.title); + selectMapSetStmt.setString(3, beatmap.artist); + selectMapSetStmt.setString(4, beatmap.creator); ResultSet rs = selectMapSetStmt.executeQuery(); List list = null; diff --git a/src/itdelatrisu/opsu/downloads/DownloadNode.java b/src/itdelatrisu/opsu/downloads/DownloadNode.java index 49de5a00..68727de2 100644 --- a/src/itdelatrisu/opsu/downloads/DownloadNode.java +++ b/src/itdelatrisu/opsu/downloads/DownloadNode.java @@ -21,9 +21,9 @@ package itdelatrisu.opsu.downloads; import itdelatrisu.opsu.ErrorHandler; import itdelatrisu.opsu.GameImage; import itdelatrisu.opsu.Options; -import itdelatrisu.opsu.OsuGroupList; import itdelatrisu.opsu.UI; import itdelatrisu.opsu.Utils; +import itdelatrisu.opsu.beatmap.BeatmapSetList; import itdelatrisu.opsu.downloads.Download.DownloadListener; import itdelatrisu.opsu.downloads.Download.Status; import itdelatrisu.opsu.downloads.servers.DownloadServer; @@ -325,7 +325,7 @@ public class DownloadNode { g.fillRect(buttonBaseX, y, buttonWidth, buttonHeight); // map is already loaded - if (OsuGroupList.get().containsBeatmapSetID(beatmapSetID)) { + if (BeatmapSetList.get().containsBeatmapSetID(beatmapSetID)) { g.setColor(Utils.COLOR_BLUE_BUTTON); g.fillRect(buttonBaseX, y, buttonWidth, buttonHeight); } diff --git a/src/itdelatrisu/opsu/objects/Circle.java b/src/itdelatrisu/opsu/objects/Circle.java index 5762c00a..fb93f3d3 100644 --- a/src/itdelatrisu/opsu/objects/Circle.java +++ b/src/itdelatrisu/opsu/objects/Circle.java @@ -22,8 +22,8 @@ import itdelatrisu.opsu.GameData; import itdelatrisu.opsu.GameData.HitObjectType; import itdelatrisu.opsu.GameImage; import itdelatrisu.opsu.GameMod; -import itdelatrisu.opsu.OsuHitObject; import itdelatrisu.opsu.Utils; +import itdelatrisu.opsu.beatmap.OsuHitObject; import itdelatrisu.opsu.states.Game; import org.newdawn.slick.Color; diff --git a/src/itdelatrisu/opsu/objects/DummyObject.java b/src/itdelatrisu/opsu/objects/DummyObject.java index 321d7dda..59e960f4 100644 --- a/src/itdelatrisu/opsu/objects/DummyObject.java +++ b/src/itdelatrisu/opsu/objects/DummyObject.java @@ -18,7 +18,7 @@ package itdelatrisu.opsu.objects; -import itdelatrisu.opsu.OsuHitObject; +import itdelatrisu.opsu.beatmap.OsuHitObject; import org.newdawn.slick.Graphics; diff --git a/src/itdelatrisu/opsu/objects/Slider.java b/src/itdelatrisu/opsu/objects/Slider.java index 57f39643..9b265c78 100644 --- a/src/itdelatrisu/opsu/objects/Slider.java +++ b/src/itdelatrisu/opsu/objects/Slider.java @@ -22,9 +22,9 @@ import itdelatrisu.opsu.GameData; import itdelatrisu.opsu.GameData.HitObjectType; import itdelatrisu.opsu.GameImage; import itdelatrisu.opsu.GameMod; -import itdelatrisu.opsu.OsuFile; -import itdelatrisu.opsu.OsuHitObject; import itdelatrisu.opsu.Utils; +import itdelatrisu.opsu.beatmap.Beatmap; +import itdelatrisu.opsu.beatmap.OsuHitObject; import itdelatrisu.opsu.objects.curves.CatmullCurve; import itdelatrisu.opsu.objects.curves.CircumscribedCircle; import itdelatrisu.opsu.objects.curves.Curve; @@ -104,9 +104,9 @@ public class Slider implements HitObject { * Initializes the Slider data type with images and dimensions. * @param container the game container * @param circleSize the map's circleSize value - * @param osu the associated OsuFile object + * @param beatmap the associated beatmap */ - public static void init(GameContainer container, float circleSize, OsuFile osu) { + public static void init(GameContainer container, float circleSize, Beatmap beatmap) { containerWidth = container.getWidth(); containerHeight = container.getHeight(); @@ -126,8 +126,8 @@ public class Slider implements HitObject { GameImage.REVERSEARROW.setImage(GameImage.REVERSEARROW.getImage().getScaledCopy(diameter, diameter)); GameImage.SLIDER_TICK.setImage(GameImage.SLIDER_TICK.getImage().getScaledCopy(diameter / 4, diameter / 4)); - sliderMultiplier = osu.sliderMultiplier; - sliderTickRate = osu.sliderTickRate; + sliderMultiplier = beatmap.sliderMultiplier; + sliderTickRate = beatmap.sliderTickRate; } /** diff --git a/src/itdelatrisu/opsu/objects/Spinner.java b/src/itdelatrisu/opsu/objects/Spinner.java index 22cdad97..7ea02ed9 100644 --- a/src/itdelatrisu/opsu/objects/Spinner.java +++ b/src/itdelatrisu/opsu/objects/Spinner.java @@ -22,10 +22,10 @@ import itdelatrisu.opsu.GameData; import itdelatrisu.opsu.GameData.HitObjectType; import itdelatrisu.opsu.GameImage; import itdelatrisu.opsu.GameMod; -import itdelatrisu.opsu.OsuHitObject; import itdelatrisu.opsu.Utils; import itdelatrisu.opsu.audio.SoundController; import itdelatrisu.opsu.audio.SoundEffect; +import itdelatrisu.opsu.beatmap.OsuHitObject; import itdelatrisu.opsu.states.Game; import org.newdawn.slick.Color; diff --git a/src/itdelatrisu/opsu/objects/curves/CatmullCurve.java b/src/itdelatrisu/opsu/objects/curves/CatmullCurve.java index 94944e13..4487b562 100644 --- a/src/itdelatrisu/opsu/objects/curves/CatmullCurve.java +++ b/src/itdelatrisu/opsu/objects/curves/CatmullCurve.java @@ -19,7 +19,7 @@ package itdelatrisu.opsu.objects.curves; import itdelatrisu.opsu.ErrorHandler; -import itdelatrisu.opsu.OsuHitObject; +import itdelatrisu.opsu.beatmap.OsuHitObject; import java.util.LinkedList; diff --git a/src/itdelatrisu/opsu/objects/curves/CircumscribedCircle.java b/src/itdelatrisu/opsu/objects/curves/CircumscribedCircle.java index 0150d145..21cd7cef 100644 --- a/src/itdelatrisu/opsu/objects/curves/CircumscribedCircle.java +++ b/src/itdelatrisu/opsu/objects/curves/CircumscribedCircle.java @@ -19,7 +19,7 @@ package itdelatrisu.opsu.objects.curves; import itdelatrisu.opsu.ErrorHandler; -import itdelatrisu.opsu.OsuHitObject; +import itdelatrisu.opsu.beatmap.OsuHitObject; import org.newdawn.slick.Color; diff --git a/src/itdelatrisu/opsu/objects/curves/Curve.java b/src/itdelatrisu/opsu/objects/curves/Curve.java index 3392ef62..63e0226c 100644 --- a/src/itdelatrisu/opsu/objects/curves/Curve.java +++ b/src/itdelatrisu/opsu/objects/curves/Curve.java @@ -19,8 +19,8 @@ package itdelatrisu.opsu.objects.curves; import itdelatrisu.opsu.GameImage; -import itdelatrisu.opsu.OsuHitObject; import itdelatrisu.opsu.Utils; +import itdelatrisu.opsu.beatmap.OsuHitObject; import org.newdawn.slick.Color; import org.newdawn.slick.Image; diff --git a/src/itdelatrisu/opsu/objects/curves/EqualDistanceMultiCurve.java b/src/itdelatrisu/opsu/objects/curves/EqualDistanceMultiCurve.java index 4cb06694..9ca0a78e 100644 --- a/src/itdelatrisu/opsu/objects/curves/EqualDistanceMultiCurve.java +++ b/src/itdelatrisu/opsu/objects/curves/EqualDistanceMultiCurve.java @@ -18,7 +18,7 @@ package itdelatrisu.opsu.objects.curves; -import itdelatrisu.opsu.OsuHitObject; +import itdelatrisu.opsu.beatmap.OsuHitObject; import java.util.Iterator; import java.util.LinkedList; diff --git a/src/itdelatrisu/opsu/objects/curves/LinearBezier.java b/src/itdelatrisu/opsu/objects/curves/LinearBezier.java index 80b1b668..74ce9ef7 100644 --- a/src/itdelatrisu/opsu/objects/curves/LinearBezier.java +++ b/src/itdelatrisu/opsu/objects/curves/LinearBezier.java @@ -18,7 +18,7 @@ package itdelatrisu.opsu.objects.curves; -import itdelatrisu.opsu.OsuHitObject; +import itdelatrisu.opsu.beatmap.OsuHitObject; import java.util.LinkedList; diff --git a/src/itdelatrisu/opsu/replay/ReplayFrame.java b/src/itdelatrisu/opsu/replay/ReplayFrame.java index 393f1494..1d42e3c3 100644 --- a/src/itdelatrisu/opsu/replay/ReplayFrame.java +++ b/src/itdelatrisu/opsu/replay/ReplayFrame.java @@ -18,7 +18,7 @@ package itdelatrisu.opsu.replay; -import itdelatrisu.opsu.OsuHitObject; +import itdelatrisu.opsu.beatmap.OsuHitObject; /** * Captures a single replay frame. diff --git a/src/itdelatrisu/opsu/states/ButtonMenu.java b/src/itdelatrisu/opsu/states/ButtonMenu.java index dde1172b..6a4786bb 100644 --- a/src/itdelatrisu/opsu/states/ButtonMenu.java +++ b/src/itdelatrisu/opsu/states/ButtonMenu.java @@ -23,14 +23,14 @@ import itdelatrisu.opsu.GameMod; import itdelatrisu.opsu.MenuButton; import itdelatrisu.opsu.Opsu; import itdelatrisu.opsu.Options; -import itdelatrisu.opsu.OsuGroupList; -import itdelatrisu.opsu.OsuGroupNode; import itdelatrisu.opsu.ScoreData; import itdelatrisu.opsu.UI; import itdelatrisu.opsu.Utils; import itdelatrisu.opsu.audio.MusicController; import itdelatrisu.opsu.audio.SoundController; import itdelatrisu.opsu.audio.SoundEffect; +import itdelatrisu.opsu.beatmap.BeatmapSetList; +import itdelatrisu.opsu.beatmap.BeatmapSetNode; import java.util.ArrayList; import java.util.List; @@ -66,9 +66,9 @@ public class ButtonMenu extends BasicGameState { BEATMAP (new Button[] { Button.CLEAR_SCORES, Button.DELETE, Button.CANCEL }) { @Override public String[] getTitle(GameContainer container, StateBasedGame game) { - OsuGroupNode node = ((ButtonMenu) game.getState(Opsu.STATE_BUTTONMENU)).getNode(); - String osuString = (node != null) ? OsuGroupList.get().getBaseNode(node.index).toString() : ""; - return new String[] { osuString, "What do you want to do with this beatmap?" }; + BeatmapSetNode node = ((ButtonMenu) game.getState(Opsu.STATE_BUTTONMENU)).getNode(); + String beatmapString = (node != null) ? BeatmapSetList.get().getBaseNode(node.index).toString() : ""; + return new String[] { beatmapString, "What do you want to do with this beatmap?" }; } @Override @@ -86,9 +86,9 @@ public class ButtonMenu extends BasicGameState { BEATMAP_DELETE_SELECT (new Button[] { Button.DELETE_GROUP, Button.DELETE_SONG, Button.CANCEL_DELETE }) { @Override public String[] getTitle(GameContainer container, StateBasedGame game) { - OsuGroupNode node = ((ButtonMenu) game.getState(Opsu.STATE_BUTTONMENU)).getNode(); - String osuString = (node != null) ? node.toString() : ""; - return new String[] { String.format("Are you sure you wish to delete '%s' from disk?", osuString) }; + BeatmapSetNode node = ((ButtonMenu) game.getState(Opsu.STATE_BUTTONMENU)).getNode(); + String beatmapString = (node != null) ? node.toString() : ""; + return new String[] { String.format("Are you sure you wish to delete '%s' from disk?", beatmapString) }; } @Override @@ -451,7 +451,7 @@ public class ButtonMenu extends BasicGameState { @Override public void click(GameContainer container, StateBasedGame game) { SoundController.playSound(SoundEffect.MENUHIT); - OsuGroupNode node = ((ButtonMenu) game.getState(Opsu.STATE_BUTTONMENU)).getNode(); + BeatmapSetNode node = ((ButtonMenu) game.getState(Opsu.STATE_BUTTONMENU)).getNode(); ((SongMenu) game.getState(Opsu.STATE_SONGMENU)).doStateActionOnLoad(MenuState.BEATMAP, node); game.enterState(Opsu.STATE_SONGMENU, new EmptyTransition(), new FadeInTransition(Color.black)); } @@ -460,8 +460,8 @@ public class ButtonMenu extends BasicGameState { @Override public void click(GameContainer container, StateBasedGame game) { SoundController.playSound(SoundEffect.MENUHIT); - OsuGroupNode node = ((ButtonMenu) game.getState(Opsu.STATE_BUTTONMENU)).getNode(); - MenuState ms = (node.osuFileIndex == -1 || node.osuFiles.size() == 1) ? + BeatmapSetNode node = ((ButtonMenu) game.getState(Opsu.STATE_BUTTONMENU)).getNode(); + MenuState ms = (node.beatmapIndex == -1 || node.beatmaps.size() == 1) ? MenuState.BEATMAP_DELETE_CONFIRM : MenuState.BEATMAP_DELETE_SELECT; ((ButtonMenu) game.getState(Opsu.STATE_BUTTONMENU)).setMenuState(ms, node); game.enterState(Opsu.STATE_BUTTONMENU); @@ -478,7 +478,7 @@ public class ButtonMenu extends BasicGameState { @Override public void click(GameContainer container, StateBasedGame game) { SoundController.playSound(SoundEffect.MENUHIT); - OsuGroupNode node = ((ButtonMenu) game.getState(Opsu.STATE_BUTTONMENU)).getNode(); + BeatmapSetNode node = ((ButtonMenu) game.getState(Opsu.STATE_BUTTONMENU)).getNode(); ((SongMenu) game.getState(Opsu.STATE_SONGMENU)).doStateActionOnLoad(MenuState.BEATMAP_DELETE_CONFIRM, node); game.enterState(Opsu.STATE_SONGMENU, new EmptyTransition(), new FadeInTransition(Color.black)); } @@ -493,7 +493,7 @@ public class ButtonMenu extends BasicGameState { @Override public void click(GameContainer container, StateBasedGame game) { SoundController.playSound(SoundEffect.MENUHIT); - OsuGroupNode node = ((ButtonMenu) game.getState(Opsu.STATE_BUTTONMENU)).getNode(); + BeatmapSetNode node = ((ButtonMenu) game.getState(Opsu.STATE_BUTTONMENU)).getNode(); ((SongMenu) game.getState(Opsu.STATE_SONGMENU)).doStateActionOnLoad(MenuState.BEATMAP_DELETE_SELECT, node); game.enterState(Opsu.STATE_SONGMENU, new EmptyTransition(), new FadeInTransition(Color.black)); } @@ -582,7 +582,7 @@ public class ButtonMenu extends BasicGameState { private MenuState menuState; /** The song node to process in the state. */ - private OsuGroupNode node; + private BeatmapSetNode node; /** The score data to process in the state. */ private ScoreData scoreData; @@ -691,7 +691,7 @@ public class ButtonMenu extends BasicGameState { * @param menuState the new menu state * @param node the song node to process in the state */ - public void setMenuState(MenuState menuState, OsuGroupNode node) { setMenuState(menuState, node, null); } + public void setMenuState(MenuState menuState, BeatmapSetNode node) { setMenuState(menuState, node, null); } /** * Changes the menu state. @@ -706,7 +706,7 @@ public class ButtonMenu extends BasicGameState { * @param node the song node to process in the state * @param scoreData the score scoreData */ - private void setMenuState(MenuState menuState, OsuGroupNode node, ScoreData scoreData) { + private void setMenuState(MenuState menuState, BeatmapSetNode node, ScoreData scoreData) { this.menuState = menuState; this.node = node; this.scoreData = scoreData; @@ -715,7 +715,7 @@ public class ButtonMenu extends BasicGameState { /** * Returns the song node being processed, or null if none. */ - private OsuGroupNode getNode() { return node; } + private BeatmapSetNode getNode() { return node; } /** * Returns the score data being processed, or null if none. diff --git a/src/itdelatrisu/opsu/states/DownloadsMenu.java b/src/itdelatrisu/opsu/states/DownloadsMenu.java index 3edc4abf..5625116e 100644 --- a/src/itdelatrisu/opsu/states/DownloadsMenu.java +++ b/src/itdelatrisu/opsu/states/DownloadsMenu.java @@ -22,8 +22,6 @@ import itdelatrisu.opsu.GameImage; import itdelatrisu.opsu.MenuButton; import itdelatrisu.opsu.Opsu; import itdelatrisu.opsu.Options; -import itdelatrisu.opsu.OsuGroupList; -import itdelatrisu.opsu.OsuGroupNode; import itdelatrisu.opsu.OsuParser; import itdelatrisu.opsu.OszUnpacker; import itdelatrisu.opsu.UI; @@ -31,6 +29,8 @@ import itdelatrisu.opsu.Utils; import itdelatrisu.opsu.audio.MusicController; import itdelatrisu.opsu.audio.SoundController; import itdelatrisu.opsu.audio.SoundEffect; +import itdelatrisu.opsu.beatmap.BeatmapSetList; +import itdelatrisu.opsu.beatmap.BeatmapSetNode; import itdelatrisu.opsu.downloads.Download; import itdelatrisu.opsu.downloads.DownloadList; import itdelatrisu.opsu.downloads.DownloadNode; @@ -482,7 +482,7 @@ public class DownloadsMenu extends BasicGameState { final DownloadNode node = nodes[index]; // check if map is already loaded - boolean isLoaded = OsuGroupList.get().containsBeatmapSetID(node.getID()); + boolean isLoaded = BeatmapSetList.get().containsBeatmapSetID(node.getID()); // track preview if (DownloadNode.resultIconContains(x, y, i)) { @@ -607,15 +607,15 @@ public class DownloadsMenu extends BasicGameState { // invoke unpacker and parser File[] dirs = OszUnpacker.unpackAllFiles(Options.getOSZDir(), Options.getBeatmapDir()); if (dirs != null && dirs.length > 0) { - OsuGroupNode node = OsuParser.parseDirectories(dirs); + BeatmapSetNode node = OsuParser.parseDirectories(dirs); if (node != null) { // stop preview previewID = -1; SoundController.stopTrack(); // initialize song list - OsuGroupList.get().reset(); - OsuGroupList.get().init(); + BeatmapSetList.get().reset(); + BeatmapSetList.get().init(); ((SongMenu) game.getState(Opsu.STATE_SONGMENU)).setFocus(node, -1, true, true); // send notification @@ -739,7 +739,7 @@ public class DownloadsMenu extends BasicGameState { switch (key) { case Input.KEY_ESCAPE: if (importThread != null) { - // beatmap importing: stop parsing OsuFiles by sending interrupt to OsuParser + // beatmap importing: stop parsing beatmaps by sending interrupt to OsuParser importThread.interrupt(); } else if (!search.getText().isEmpty()) { // clear search text diff --git a/src/itdelatrisu/opsu/states/Game.java b/src/itdelatrisu/opsu/states/Game.java index 8efebb3e..70704e10 100644 --- a/src/itdelatrisu/opsu/states/Game.java +++ b/src/itdelatrisu/opsu/states/Game.java @@ -25,18 +25,18 @@ import itdelatrisu.opsu.GameMod; import itdelatrisu.opsu.MenuButton; import itdelatrisu.opsu.Opsu; import itdelatrisu.opsu.Options; -import itdelatrisu.opsu.OsuFile; -import itdelatrisu.opsu.OsuHitObject; import itdelatrisu.opsu.OsuParser; import itdelatrisu.opsu.ScoreData; -import itdelatrisu.opsu.TimingPoint; import itdelatrisu.opsu.UI; import itdelatrisu.opsu.Utils; import itdelatrisu.opsu.audio.HitSound; import itdelatrisu.opsu.audio.MusicController; import itdelatrisu.opsu.audio.SoundController; import itdelatrisu.opsu.audio.SoundEffect; -import itdelatrisu.opsu.db.OsuDB; +import itdelatrisu.opsu.beatmap.Beatmap; +import itdelatrisu.opsu.beatmap.OsuHitObject; +import itdelatrisu.opsu.beatmap.TimingPoint; +import itdelatrisu.opsu.db.BeatmapDB; import itdelatrisu.opsu.db.ScoreDB; import itdelatrisu.opsu.objects.Circle; import itdelatrisu.opsu.objects.DummyObject; @@ -96,8 +96,8 @@ public class Game extends BasicGameState { /** Stack position offset modifier. */ private static final float STACK_OFFSET_MODIFIER = 0.05f; - /** The associated OsuFile object. */ - private OsuFile osu; + /** The associated beatmap. */ + private Beatmap beatmap; /** The associated GameData object. */ private GameData data; @@ -254,7 +254,7 @@ public class Game extends BasicGameState { trackPosition = pauseTime; else if (deathTime > -1) // "Easy" mod: health bar increasing trackPosition = deathTime; - int firstObjectTime = osu.objects[0].getTime(); + int firstObjectTime = beatmap.objects[0].getTime(); int timeDiff = firstObjectTime - trackPosition; g.setBackground(Color.black); @@ -273,7 +273,7 @@ public class Game extends BasicGameState { else dimLevel = 1f; } - if (Options.isDefaultPlayfieldForced() || !osu.drawBG(width, height, dimLevel, false)) { + if (Options.isDefaultPlayfieldForced() || !beatmap.drawBG(width, height, dimLevel, false)) { Image playfield = GameImage.PLAYFIELD.getImage(); playfield.setAlpha(dimLevel); playfield.draw(); @@ -292,7 +292,7 @@ public class Game extends BasicGameState { float[] autoXY = null; if (isLeadIn()) { // lead-in - float progress = Math.max((float) (leadInTime - osu.audioLeadIn) / approachTime, 0f); + float progress = Math.max((float) (leadInTime - beatmap.audioLeadIn) / approachTime, 0f); autoMouseY = (int) (height / (2f - progress)); } else if (objectIndex == 0 && trackPosition < firstObjectTime) { // before first object @@ -301,20 +301,20 @@ public class Game extends BasicGameState { float[] xy = hitObjects[0].getPointAt(trackPosition); autoXY = getPointAt(autoMouseX, autoMouseY, xy[0], xy[1], 1f - ((float) timeDiff / Math.min(approachTime, firstObjectTime))); } - } else if (objectIndex < osu.objects.length) { + } else if (objectIndex < beatmap.objects.length) { // normal object - int objectTime = osu.objects[objectIndex].getTime(); + int objectTime = beatmap.objects[objectIndex].getTime(); if (trackPosition < objectTime) { float[] xyStart = hitObjects[objectIndex - 1].getPointAt(trackPosition); int startTime = hitObjects[objectIndex - 1].getEndTime(); - if (osu.breaks != null && breakIndex < osu.breaks.size()) { + if (beatmap.breaks != null && breakIndex < beatmap.breaks.size()) { // starting a break: keep cursor at previous hit object position - if (breakTime > 0 || objectTime > osu.breaks.get(breakIndex)) + if (breakTime > 0 || objectTime > beatmap.breaks.get(breakIndex)) autoXY = xyStart; // after a break ends: move startTime to break end time else if (breakIndex > 1) { - int lastBreakEndTime = osu.breaks.get(breakIndex - 1); + int lastBreakEndTime = beatmap.breaks.get(breakIndex - 1); if (objectTime > lastBreakEndTime && startTime < lastBreakEndTime) startTime = lastBreakEndTime; } @@ -326,8 +326,8 @@ public class Game extends BasicGameState { // hit circles: show a mouse press int offset300 = hitResultOffset[GameData.HIT_300]; - if ((osu.objects[objectIndex].isCircle() && objectTime - trackPosition < offset300) || - (osu.objects[objectIndex - 1].isCircle() && trackPosition - osu.objects[objectIndex - 1].getTime() < offset300)) + if ((beatmap.objects[objectIndex].isCircle() && objectTime - trackPosition < offset300) || + (beatmap.objects[objectIndex - 1].isCircle() && trackPosition - beatmap.objects[objectIndex - 1].getTime() < offset300)) autoMousePressed = true; } } else { @@ -388,12 +388,12 @@ public class Game extends BasicGameState { } // break periods - if (osu.breaks != null && breakIndex < osu.breaks.size() && breakTime > 0) { - int endTime = osu.breaks.get(breakIndex); + if (beatmap.breaks != null && breakIndex < beatmap.breaks.size() && breakTime > 0) { + int endTime = beatmap.breaks.get(breakIndex); int breakLength = endTime - breakTime; // letterbox effect (black bars on top/bottom) - if (osu.letterboxInBreaks && breakLength >= 4000) { + if (beatmap.letterboxInBreaks && breakLength >= 4000) { g.setColor(Color.black); g.fillRect(0, 0, width, height * 0.125f); g.fillRect(0, height * 0.875f, width, height * 0.125f); @@ -441,7 +441,7 @@ public class Game extends BasicGameState { // skip beginning if (objectIndex == 0 && - trackPosition < osu.objects[0].getTime() - SKIP_OFFSET) + trackPosition < beatmap.objects[0].getTime() - SKIP_OFFSET) skipButton.draw(); // show retries @@ -465,7 +465,7 @@ public class Game extends BasicGameState { trackPosition = (leadInTime - Options.getMusicOffset()) * -1; // render approach circles during song lead-in // countdown - if (osu.countdown > 0) { + if (beatmap.countdown > 0) { float speedModifier = GameMod.getSpeedMultiplier() * playbackSpeed.getModifier(); timeDiff = firstObjectTime - trackPosition; if (timeDiff >= 500 * speedModifier && timeDiff < 3000 * speedModifier) { @@ -667,11 +667,11 @@ public class Game extends BasicGameState { replayFrames.getFirst().setTimeDiff(replaySkipTime * -1); replayFrames.addFirst(ReplayFrame.getStartFrame(replaySkipTime)); replayFrames.addFirst(ReplayFrame.getStartFrame(0)); - Replay r = data.getReplay(replayFrames.toArray(new ReplayFrame[replayFrames.size()]), osu); + Replay r = data.getReplay(replayFrames.toArray(new ReplayFrame[replayFrames.size()]), beatmap); if (r != null && !unranked) r.save(); } - ScoreData score = data.getScoreData(osu); + ScoreData score = data.getScoreData(beatmap); // add score to database if (!unranked && !isReplay) @@ -683,8 +683,8 @@ public class Game extends BasicGameState { } // timing points - if (timingPointIndex < osu.timingPoints.size()) { - TimingPoint timingPoint = osu.timingPoints.get(timingPointIndex); + if (timingPointIndex < beatmap.timingPoints.size()) { + TimingPoint timingPoint = beatmap.timingPoints.get(timingPointIndex); if (trackPosition >= timingPoint.getTime()) { setBeatLength(timingPoint, true); timingPointIndex++; @@ -692,12 +692,12 @@ public class Game extends BasicGameState { } // song beginning - if (objectIndex == 0 && trackPosition < osu.objects[0].getTime()) + if (objectIndex == 0 && trackPosition < beatmap.objects[0].getTime()) return; // nothing to do here // break periods - if (osu.breaks != null && breakIndex < osu.breaks.size()) { - int breakValue = osu.breaks.get(breakIndex); + if (beatmap.breaks != null && breakIndex < beatmap.breaks.size()) { + int breakValue = beatmap.breaks.get(breakIndex); if (breakTime > 0) { // in a break period if (trackPosition < breakValue) return; @@ -749,10 +749,10 @@ public class Game extends BasicGameState { // update objects (loop in unlikely event of any skipped indexes) boolean keyPressed = keys != ReplayFrame.KEY_NONE; - while (objectIndex < hitObjects.length && trackPosition > osu.objects[objectIndex].getTime()) { + while (objectIndex < hitObjects.length && trackPosition > beatmap.objects[objectIndex].getTime()) { // check if we've already passed the next object's start time boolean overlap = (objectIndex + 1 < hitObjects.length && - trackPosition > osu.objects[objectIndex + 1].getTime() - hitResultOffset[GameData.HIT_300]); + trackPosition > beatmap.objects[objectIndex + 1].getTime() - hitResultOffset[GameData.HIT_300]); // update hit object and check completion status if (hitObjects[objectIndex].update(overlap, delta, mouseX, mouseY, keyPressed, trackPosition)) @@ -791,7 +791,7 @@ public class Game extends BasicGameState { } // pause game - if (pauseTime < 0 && breakTime <= 0 && trackPosition >= osu.objects[0].getTime()) { + if (pauseTime < 0 && breakTime <= 0 && trackPosition >= beatmap.objects[0].getTime()) { pausedMouseX = mouseX; pausedMouseY = mouseY; pausePulse = 0f; @@ -808,7 +808,7 @@ public class Game extends BasicGameState { // restart if (input.isKeyDown(Input.KEY_RCONTROL) || input.isKeyDown(Input.KEY_LCONTROL)) { try { - if (trackPosition < osu.objects[0].getTime()) + if (trackPosition < beatmap.objects[0].getTime()) retries--; // don't count this retry (cancel out later increment) restart = Restart.MANUAL; enter(container, game); @@ -835,7 +835,7 @@ public class Game extends BasicGameState { // load checkpoint if (input.isKeyDown(Input.KEY_RCONTROL) || input.isKeyDown(Input.KEY_LCONTROL)) { int checkpoint = Options.getCheckpoint(); - if (checkpoint == 0 || checkpoint > osu.endTime) + if (checkpoint == 0 || checkpoint > beatmap.endTime) break; // invalid checkpoint try { restart = Restart.MANUAL; @@ -852,10 +852,10 @@ public class Game extends BasicGameState { MusicController.setPosition(checkpoint); MusicController.setPitch(GameMod.getSpeedMultiplier() * playbackSpeed.getModifier()); while (objectIndex < hitObjects.length && - osu.objects[objectIndex++].getTime() <= checkpoint) + beatmap.objects[objectIndex++].getTime() <= checkpoint) ; objectIndex--; - lastReplayTime = osu.objects[objectIndex].getTime(); + lastReplayTime = beatmap.objects[objectIndex].getTime(); } catch (SlickException e) { ErrorHandler.error("Failed to load checkpoint.", e, false); } @@ -905,7 +905,7 @@ public class Game extends BasicGameState { // mouse wheel: pause the game if (button == Input.MOUSE_MIDDLE_BUTTON && !Options.isMouseWheelDisabled()) { int trackPosition = MusicController.getPosition(); - if (pauseTime < 0 && breakTime <= 0 && trackPosition >= osu.objects[0].getTime()) { + if (pauseTime < 0 && breakTime <= 0 && trackPosition >= beatmap.objects[0].getTime()) { pausedMouseX = x; pausedMouseY = y; pausePulse = 0f; @@ -1021,8 +1021,8 @@ public class Game extends BasicGameState { throws SlickException { UI.enter(); - if (osu == null || osu.objects == null) - throw new RuntimeException("Running game with no OsuFile loaded."); + if (beatmap == null || beatmap.objects == null) + throw new RuntimeException("Running game with no beatmap loaded."); // grab the mouse (not working for touchscreen) // container.setMouseGrabbed(true); @@ -1044,8 +1044,8 @@ public class Game extends BasicGameState { resetGameData(); // load the first timingPoint for stacking - if (!osu.timingPoints.isEmpty()) { - TimingPoint timingPoint = osu.timingPoints.get(0); + if (!beatmap.timingPoints.isEmpty()) { + TimingPoint timingPoint = beatmap.timingPoints.get(0); if (!timingPoint.isInherited()) { setBeatLength(timingPoint, true); timingPointIndex++; @@ -1053,20 +1053,20 @@ public class Game extends BasicGameState { } // initialize object maps - for (int i = 0; i < osu.objects.length; i++) { - OsuHitObject hitObject = osu.objects[i]; + for (int i = 0; i < beatmap.objects.length; i++) { + OsuHitObject hitObject = beatmap.objects[i]; // is this the last note in the combo? boolean comboEnd = false; - if (i + 1 < osu.objects.length && osu.objects[i + 1].isNewCombo()) + if (i + 1 < beatmap.objects.length && beatmap.objects[i + 1].isNewCombo()) comboEnd = true; - Color color = osu.combo[hitObject.getComboIndex()]; + Color color = beatmap.combo[hitObject.getComboIndex()]; // pass beatLength to hit objects int hitObjectTime = hitObject.getTime(); - while (timingPointIndex < osu.timingPoints.size()) { - TimingPoint timingPoint = osu.timingPoints.get(timingPointIndex); + while (timingPointIndex < beatmap.timingPoints.size()) { + TimingPoint timingPoint = beatmap.timingPoints.get(timingPointIndex); if (timingPoint.getTime() > hitObjectTime) break; setBeatLength(timingPoint, false); @@ -1095,8 +1095,8 @@ public class Game extends BasicGameState { // load the first timingPoint timingPointIndex = 0; beatLengthBase = beatLength = 1; - if (!osu.timingPoints.isEmpty()) { - TimingPoint timingPoint = osu.timingPoints.get(0); + if (!beatmap.timingPoints.isEmpty()) { + TimingPoint timingPoint = beatmap.timingPoints.get(0); if (!timingPoint.isInherited()) { setBeatLength(timingPoint, true); timingPointIndex++; @@ -1140,7 +1140,7 @@ public class Game extends BasicGameState { replayFrames.add(new ReplayFrame(0, 0, input.getMouseX(), input.getMouseY(), 0)); } - leadInTime = osu.audioLeadIn + approachTime; + leadInTime = beatmap.audioLeadIn + approachTime; restart = Restart.FALSE; // needs to play before setting position to resume without lag later @@ -1181,27 +1181,27 @@ public class Game extends BasicGameState { private void drawHitObjects(Graphics g, int trackPosition) { // include previous object in follow points int lastObjectIndex = -1; - if (objectIndex > 0 && objectIndex < osu.objects.length && - trackPosition < osu.objects[objectIndex].getTime() && !osu.objects[objectIndex - 1].isSpinner()) + if (objectIndex > 0 && objectIndex < beatmap.objects.length && + trackPosition < beatmap.objects[objectIndex].getTime() && !beatmap.objects[objectIndex - 1].isSpinner()) lastObjectIndex = objectIndex - 1; // draw hit objects in reverse order, or else overlapping objects are unreadable Stack stack = new Stack(); - for (int index = objectIndex; index < hitObjects.length && osu.objects[index].getTime() < trackPosition + approachTime; index++) { + for (int index = objectIndex; index < hitObjects.length && beatmap.objects[index].getTime() < trackPosition + approachTime; index++) { stack.add(index); // draw follow points if (!Options.isFollowPointEnabled()) continue; - if (osu.objects[index].isSpinner()) { + if (beatmap.objects[index].isSpinner()) { lastObjectIndex = -1; continue; } - if (lastObjectIndex != -1 && !osu.objects[index].isNewCombo()) { + if (lastObjectIndex != -1 && !beatmap.objects[index].isNewCombo()) { // calculate points final int followPointInterval = container.getHeight() / 14; int lastObjectEndTime = hitObjects[lastObjectIndex].getEndTime() + 1; - int objectStartTime = osu.objects[index].getTime(); + int objectStartTime = beatmap.objects[index].getTime(); float[] startXY = hitObjects[lastObjectIndex].getPointAt(lastObjectEndTime); float[] endXY = hitObjects[index].getPointAt(objectStartTime); float xDiff = endXY[0] - startXY[0]; @@ -1257,23 +1257,23 @@ public class Game extends BasicGameState { } /** - * Loads all required data from an OsuFile. - * @param osu the OsuFile to load + * Loads all required data from a beatmap. + * @param beatmap the beatmap to load */ - public void loadOsuFile(OsuFile osu) { - this.osu = osu; - Display.setTitle(String.format("%s - %s", game.getTitle(), osu.toString())); - if (osu.timingPoints == null || osu.combo == null) - OsuDB.load(osu, OsuDB.LOAD_ARRAY); - OsuParser.parseHitObjects(osu); - HitSound.setDefaultSampleSet(osu.sampleSet); + public void loadBeatmap(Beatmap beatmap) { + this.beatmap = beatmap; + Display.setTitle(String.format("%s - %s", game.getTitle(), beatmap.toString())); + if (beatmap.timingPoints == null || beatmap.combo == null) + BeatmapDB.load(beatmap, BeatmapDB.LOAD_ARRAY); + OsuParser.parseHitObjects(beatmap); + HitSound.setDefaultSampleSet(beatmap.sampleSet); } /** * Resets all game data and structures. */ public void resetGameData() { - hitObjects = new HitObject[osu.objects.length]; + hitObjects = new HitObject[beatmap.objects.length]; data.clear(); objectIndex = 0; breakIndex = 0; @@ -1308,7 +1308,7 @@ public class Game extends BasicGameState { * @return true if skipped, false otherwise */ private synchronized boolean skipIntro() { - int firstObjectTime = osu.objects[0].getTime(); + int firstObjectTime = beatmap.objects[0].getTime(); int trackPosition = MusicController.getPosition(); if (objectIndex == 0 && trackPosition < firstObjectTime - SKIP_OFFSET) { if (isLeadIn()) { @@ -1336,7 +1336,7 @@ public class Game extends BasicGameState { int height = container.getHeight(); // set images - File parent = osu.getFile().getParentFile(); + File parent = beatmap.getFile().getParentFile(); for (GameImage img : GameImage.values()) { if (img.isSkinnable()) { img.setDefaultImage(); @@ -1365,10 +1365,10 @@ public class Game extends BasicGameState { private void setMapModifiers() { // map-based properties, re-initialized each game float multiplier = GameMod.getDifficultyMultiplier(); - float circleSize = Math.min(osu.circleSize * multiplier, 10f); - float approachRate = Math.min(osu.approachRate * multiplier, 10f); - float overallDifficulty = Math.min(osu.overallDifficulty * multiplier, 10f); - float HPDrainRate = Math.min(osu.HPDrainRate * multiplier, 10f); + float circleSize = Math.min(beatmap.circleSize * multiplier, 10f); + float approachRate = Math.min(beatmap.approachRate * multiplier, 10f); + float overallDifficulty = Math.min(beatmap.overallDifficulty * multiplier, 10f); + float HPDrainRate = Math.min(beatmap.HPDrainRate * multiplier, 10f); // fixed difficulty overrides if (Options.getFixedCS() > 0f) @@ -1387,7 +1387,7 @@ public class Game extends BasicGameState { // initialize objects Circle.init(container, circleSize); - Slider.init(container, circleSize, osu); + Slider.init(container, circleSize, beatmap); Spinner.init(container); // approachRate (hit object approach time) @@ -1522,7 +1522,7 @@ public class Game extends BasicGameState { if (objectIndex >= hitObjects.length) // nothing to do here return; - OsuHitObject hitObject = osu.objects[objectIndex]; + OsuHitObject hitObject = beatmap.objects[objectIndex]; // circles if (hitObject.isCircle() && hitObjects[objectIndex].mousePressed(x, y, trackPosition)) @@ -1582,14 +1582,14 @@ public class Game extends BasicGameState { return; int width = container.getWidth(), height = container.getHeight(); - boolean firstObject = (objectIndex == 0 && trackPosition < osu.objects[0].getTime()); + boolean firstObject = (objectIndex == 0 && trackPosition < beatmap.objects[0].getTime()); if (isLeadIn()) { // lead-in: expand area - float progress = Math.max((float) (leadInTime - osu.audioLeadIn) / approachTime, 0f); + float progress = Math.max((float) (leadInTime - beatmap.audioLeadIn) / approachTime, 0f); flashlightRadius = width - (int) ((width - (height * 2 / 3)) * progress); } else if (firstObject) { // before first object: shrink area - int timeDiff = osu.objects[0].getTime() - trackPosition; + int timeDiff = beatmap.objects[0].getTime() - trackPosition; flashlightRadius = width; if (timeDiff < approachTime) { float progress = (float) timeDiff / approachTime; @@ -1605,10 +1605,10 @@ public class Game extends BasicGameState { targetRadius = height / 2; else targetRadius = height / 3; - if (osu.breaks != null && breakIndex < osu.breaks.size() && breakTime > 0) { + if (beatmap.breaks != null && breakIndex < beatmap.breaks.size() && breakTime > 0) { // breaks: expand at beginning, shrink at end flashlightRadius = targetRadius; - int endTime = osu.breaks.get(breakIndex); + int endTime = beatmap.breaks.get(breakIndex); int breakLength = endTime - breakTime; if (breakLength > approachTime * 3) { float progress = 1f; @@ -1642,7 +1642,7 @@ public class Game extends BasicGameState { private void calculateStacks() { // reverse pass for stack calculation for (int i = hitObjects.length - 1; i > 0; i--) { - OsuHitObject hitObjectI = osu.objects[i]; + OsuHitObject hitObjectI = beatmap.objects[i]; // already calculated if (hitObjectI.getStack() != 0 || hitObjectI.isSpinner()) @@ -1650,12 +1650,12 @@ public class Game extends BasicGameState { // search for hit objects in stack for (int n = i - 1; n >= 0; n--) { - OsuHitObject hitObjectN = osu.objects[n]; + OsuHitObject hitObjectN = beatmap.objects[n]; if (hitObjectN.isSpinner()) continue; // check if in range stack calculation - float timeI = hitObjectI.getTime() - (STACK_TIMEOUT * osu.stackLeniency); + float timeI = hitObjectI.getTime() - (STACK_TIMEOUT * beatmap.stackLeniency); float timeN = hitObjectN.isSlider() ? hitObjects[n].getEndTime() : hitObjectN.getTime(); if (timeI > timeN) break; @@ -1671,7 +1671,7 @@ public class Game extends BasicGameState { if (distance < STACK_LENIENCE * OsuHitObject.getXMultiplier()) { int offset = hitObjectI.getStack() - hitObjectN.getStack() + 1; for (int j = n + 1; j <= i; j++) { - OsuHitObject hitObjectJ = osu.objects[j]; + OsuHitObject hitObjectJ = beatmap.objects[j]; p1 = hitObjects[j].getPointAt(hitObjectJ.getTime()); distance = Utils.distance(p1[0], p1[1], p2[0], p2[1]); @@ -1697,7 +1697,7 @@ public class Game extends BasicGameState { // update hit object positions for (int i = 0; i < hitObjects.length; i++) { - if (osu.objects[i].getStack() != 0) + if (beatmap.objects[i].getStack() != 0) hitObjects[i].updatePosition(); } } diff --git a/src/itdelatrisu/opsu/states/GamePauseMenu.java b/src/itdelatrisu/opsu/states/GamePauseMenu.java index 4eec52f5..dd8a9de9 100644 --- a/src/itdelatrisu/opsu/states/GamePauseMenu.java +++ b/src/itdelatrisu/opsu/states/GamePauseMenu.java @@ -132,7 +132,7 @@ public class GamePauseMenu extends BasicGameState { if (gameState.getRestart() == Game.Restart.LOSE) { SoundController.playSound(SoundEffect.MENUBACK); ((SongMenu) game.getState(Opsu.STATE_SONGMENU)).resetGameDataOnLoad(); - MusicController.playAt(MusicController.getOsuFile().previewTime, true); + MusicController.playAt(MusicController.getBeatmap().previewTime, true); UI.resetCursor(); game.enterState(Opsu.STATE_SONGMENU, new FadeOutTransition(Color.black), new FadeInTransition(Color.black)); } else { @@ -183,7 +183,7 @@ public class GamePauseMenu extends BasicGameState { SoundController.playSound(SoundEffect.MENUBACK); ((SongMenu) game.getState(Opsu.STATE_SONGMENU)).resetGameDataOnLoad(); if (loseState) - MusicController.playAt(MusicController.getOsuFile().previewTime, true); + MusicController.playAt(MusicController.getBeatmap().previewTime, true); else MusicController.resume(); UI.resetCursor(); diff --git a/src/itdelatrisu/opsu/states/GameRanking.java b/src/itdelatrisu/opsu/states/GameRanking.java index 327f9c41..e0380762 100644 --- a/src/itdelatrisu/opsu/states/GameRanking.java +++ b/src/itdelatrisu/opsu/states/GameRanking.java @@ -23,12 +23,12 @@ import itdelatrisu.opsu.GameImage; import itdelatrisu.opsu.MenuButton; import itdelatrisu.opsu.Opsu; import itdelatrisu.opsu.Options; -import itdelatrisu.opsu.OsuFile; import itdelatrisu.opsu.UI; import itdelatrisu.opsu.Utils; import itdelatrisu.opsu.audio.MusicController; import itdelatrisu.opsu.audio.SoundController; import itdelatrisu.opsu.audio.SoundEffect; +import itdelatrisu.opsu.beatmap.Beatmap; import itdelatrisu.opsu.replay.Replay; import java.io.FileNotFoundException; @@ -102,14 +102,14 @@ public class GameRanking extends BasicGameState { int width = container.getWidth(); int height = container.getHeight(); - OsuFile osu = MusicController.getOsuFile(); + Beatmap beatmap = MusicController.getBeatmap(); // background - if (!osu.drawBG(width, height, 0.7f, true)) + if (!beatmap.drawBG(width, height, 0.7f, true)) GameImage.PLAYFIELD.getImage().draw(0,0); // ranking screen elements - data.drawRankingElements(g, osu); + data.drawRankingElements(g, beatmap); // buttons replayButton.draw(); @@ -201,8 +201,8 @@ public class GameRanking extends BasicGameState { } if (returnToGame) { - OsuFile osu = MusicController.getOsuFile(); - gameState.loadOsuFile(osu); + Beatmap beatmap = MusicController.getBeatmap(); + gameState.loadBeatmap(beatmap); SoundController.playSound(SoundEffect.MENUHIT); game.enterState(Opsu.STATE_GAME, new FadeOutTransition(Color.black), new FadeInTransition(Color.black)); return; diff --git a/src/itdelatrisu/opsu/states/MainMenu.java b/src/itdelatrisu/opsu/states/MainMenu.java index 37348bfd..651bea8b 100644 --- a/src/itdelatrisu/opsu/states/MainMenu.java +++ b/src/itdelatrisu/opsu/states/MainMenu.java @@ -24,14 +24,14 @@ import itdelatrisu.opsu.MenuButton; import itdelatrisu.opsu.MenuButton.Expand; import itdelatrisu.opsu.Opsu; import itdelatrisu.opsu.Options; -import itdelatrisu.opsu.OsuFile; -import itdelatrisu.opsu.OsuGroupList; -import itdelatrisu.opsu.OsuGroupNode; import itdelatrisu.opsu.UI; import itdelatrisu.opsu.Utils; import itdelatrisu.opsu.audio.MusicController; import itdelatrisu.opsu.audio.SoundController; import itdelatrisu.opsu.audio.SoundEffect; +import itdelatrisu.opsu.beatmap.Beatmap; +import itdelatrisu.opsu.beatmap.BeatmapSetList; +import itdelatrisu.opsu.beatmap.BeatmapSetNode; import itdelatrisu.opsu.downloads.Updater; import itdelatrisu.opsu.states.ButtonMenu.MenuState; @@ -91,7 +91,7 @@ public class MainMenu extends BasicGameState { private MenuButton updateButton; /** Application start time, for drawing the total running time. */ - private long osuStartTime; + private long programStartTime; /** Indexes of previous songs. */ private Stack previous; @@ -127,7 +127,7 @@ public class MainMenu extends BasicGameState { this.game = game; this.input = container.getInput(); - osuStartTime = System.currentTimeMillis(); + programStartTime = System.currentTimeMillis(); previous = new Stack(); int width = container.getWidth(); @@ -199,9 +199,9 @@ public class MainMenu extends BasicGameState { int height = container.getHeight(); // draw background - OsuFile osu = MusicController.getOsuFile(); + Beatmap beatmap = MusicController.getBeatmap(); if (Options.isDynamicBackgroundEnabled() && - osu != null && osu.drawBG(width, height, bgAlpha, true)) + beatmap != null && beatmap.drawBG(width, height, bgAlpha, true)) ; else { Image bg = GameImage.MENU_BG.getImage(); @@ -240,7 +240,7 @@ public class MainMenu extends BasicGameState { g.setColor((musicPositionBarContains(mouseX, mouseY)) ? BG_HOVER : BG_NORMAL); g.fillRoundRect(musicBarX, musicBarY, musicBarWidth, musicBarHeight, 4); g.setColor(Color.white); - if (!MusicController.isTrackLoading() && osu != null) { + if (!MusicController.isTrackLoading() && beatmap != null) { float musicBarPosition = Math.min((float) MusicController.getPosition() / MusicController.getDuration(), 1f); g.fillRoundRect(musicBarX, musicBarY, musicBarWidth * musicBarPosition, musicBarHeight, 4); } @@ -274,17 +274,17 @@ public class MainMenu extends BasicGameState { g.setFont(Utils.FONT_MEDIUM); float lineHeight = Utils.FONT_MEDIUM.getLineHeight() * 0.925f; g.drawString(String.format("Loaded %d songs and %d beatmaps.", - OsuGroupList.get().getMapSetCount(), OsuGroupList.get().getMapCount()), marginX, topMarginY); + BeatmapSetList.get().getMapSetCount(), BeatmapSetList.get().getMapCount()), marginX, topMarginY); if (MusicController.isTrackLoading()) g.drawString("Track loading...", marginX, topMarginY + lineHeight); else if (MusicController.trackExists()) { if (Options.useUnicodeMetadata()) // load glyphs - Utils.loadGlyphs(Utils.FONT_MEDIUM, osu.titleUnicode, osu.artistUnicode); + Utils.loadGlyphs(Utils.FONT_MEDIUM, beatmap.titleUnicode, beatmap.artistUnicode); g.drawString((MusicController.isPlaying()) ? "Now Playing:" : "Paused:", marginX, topMarginY + lineHeight); - g.drawString(String.format("%s: %s", osu.getArtist(), osu.getTitle()), marginX + 25, topMarginY + (lineHeight * 2)); + g.drawString(String.format("%s: %s", beatmap.getArtist(), beatmap.getTitle()), marginX + 25, topMarginY + (lineHeight * 2)); } g.drawString(String.format("opsu! has been running for %s.", - Utils.getTimeString((int) (System.currentTimeMillis() - osuStartTime) / 1000)), + Utils.getTimeString((int) (System.currentTimeMillis() - programStartTime) / 1000)), marginX, height - bottomMarginY - (lineHeight * 2)); g.drawString(String.format("It is currently %s.", new SimpleDateFormat("h:mm a").format(new Date())), @@ -455,7 +455,7 @@ public class MainMenu extends BasicGameState { } else if (musicPrevious.contains(x, y)) { if (!previous.isEmpty()) { SongMenu menu = (SongMenu) game.getState(Opsu.STATE_SONGMENU); - menu.setFocus(OsuGroupList.get().getBaseNode(previous.pop()), -1, true, false); + menu.setFocus(BeatmapSetList.get().getBaseNode(previous.pop()), -1, true, false); if (Options.isDynamicBackgroundEnabled()) bgAlpha = 0f; } else @@ -603,10 +603,10 @@ public class MainMenu extends BasicGameState { private void nextTrack() { boolean isTheme = MusicController.isThemePlaying(); SongMenu menu = (SongMenu) game.getState(Opsu.STATE_SONGMENU); - OsuGroupNode node = menu.setFocus(OsuGroupList.get().getRandomNode(), -1, true, false); + BeatmapSetNode node = menu.setFocus(BeatmapSetList.get().getRandomNode(), -1, true, false); boolean sameAudio = false; if (node != null) { - sameAudio = MusicController.getOsuFile().audioFilename.equals(node.osuFiles.get(0).audioFilename); + sameAudio = MusicController.getBeatmap().audioFilename.equals(node.beatmaps.get(0).audioFilename); if (!isTheme && !sameAudio) previous.add(node.index); } @@ -619,7 +619,7 @@ public class MainMenu extends BasicGameState { */ private void enterSongMenu() { int state = Opsu.STATE_SONGMENU; - if (OsuGroupList.get().getMapSetCount() == 0) { + if (BeatmapSetList.get().getMapSetCount() == 0) { ((DownloadsMenu) game.getState(Opsu.STATE_DOWNLOADSMENU)).notifyOnLoad("Download some beatmaps to get started!"); state = Opsu.STATE_DOWNLOADSMENU; } diff --git a/src/itdelatrisu/opsu/states/SongMenu.java b/src/itdelatrisu/opsu/states/SongMenu.java index ff5d38b6..36468072 100644 --- a/src/itdelatrisu/opsu/states/SongMenu.java +++ b/src/itdelatrisu/opsu/states/SongMenu.java @@ -25,9 +25,6 @@ import itdelatrisu.opsu.GameMod; import itdelatrisu.opsu.MenuButton; import itdelatrisu.opsu.Opsu; import itdelatrisu.opsu.Options; -import itdelatrisu.opsu.OsuFile; -import itdelatrisu.opsu.OsuGroupList; -import itdelatrisu.opsu.OsuGroupNode; import itdelatrisu.opsu.OsuParser; import itdelatrisu.opsu.OszUnpacker; import itdelatrisu.opsu.ScoreData; @@ -38,7 +35,10 @@ import itdelatrisu.opsu.audio.MultiClip; import itdelatrisu.opsu.audio.MusicController; import itdelatrisu.opsu.audio.SoundController; import itdelatrisu.opsu.audio.SoundEffect; -import itdelatrisu.opsu.db.OsuDB; +import itdelatrisu.opsu.beatmap.Beatmap; +import itdelatrisu.opsu.beatmap.BeatmapSetList; +import itdelatrisu.opsu.beatmap.BeatmapSetNode; +import itdelatrisu.opsu.db.BeatmapDB; import itdelatrisu.opsu.db.ScoreDB; import itdelatrisu.opsu.states.ButtonMenu.MenuState; @@ -91,28 +91,28 @@ public class SongMenu extends BasicGameState { /** Line width of the header/footer divider. */ private static final int DIVIDER_LINE_WIDTH = 4; - /** Song node class representing an OsuGroupNode and file index. */ + /** Song node class representing an BeatmapSetNode and file index. */ private static class SongNode { /** Song node. */ - private OsuGroupNode node; + private BeatmapSetNode node; /** File index. */ private int index; /** * Constructor. - * @param node the OsuGroupNode + * @param node the BeatmapSetNode * @param index the file index */ - public SongNode(OsuGroupNode node, int index) { + public SongNode(BeatmapSetNode node, int index) { this.node = node; this.index = index; } /** - * Returns the associated OsuGroupNode. + * Returns the associated BeatmapSetNode. */ - public OsuGroupNode getNode() { return node; } + public BeatmapSetNode getNode() { return node; } /** * Returns the associated file index. @@ -121,10 +121,10 @@ public class SongMenu extends BasicGameState { } /** Current start node (topmost menu entry). */ - private OsuGroupNode startNode; + private BeatmapSetNode startNode; /** Current focused (selected) node. */ - private OsuGroupNode focusNode; + private BeatmapSetNode focusNode; /** The base node of the previous focus node. */ private SongNode oldFocusNode = null; @@ -172,7 +172,7 @@ public class SongMenu extends BasicGameState { private MenuState stateAction; /** If non-null, the node that stateAction acts upon. */ - private OsuGroupNode stateActionNode; + private BeatmapSetNode stateActionNode; /** If non-null, the score data that stateAction acts upon. */ private ScoreData stateActionScore; @@ -292,13 +292,13 @@ public class SongMenu extends BasicGameState { // background if (focusNode != null) { - OsuFile focusNodeOsu = focusNode.osuFiles.get(focusNode.osuFileIndex); - if (!focusNodeOsu.drawBG(width, height, 1.0f, true)) + Beatmap focusNodeBeatmap = focusNode.beatmaps.get(focusNode.beatmapIndex); + if (!focusNodeBeatmap.drawBG(width, height, 1.0f, true)) GameImage.PLAYFIELD.getImage().draw(); } // song buttons - OsuGroupNode node = startNode; + BeatmapSetNode node = startNode; int songButtonIndex = 0; if (node != null && node.prev != null) { node = node.prev; @@ -339,8 +339,8 @@ public class SongMenu extends BasicGameState { if (songInfo == null) { songInfo = focusNode.getInfo(); if (Options.useUnicodeMetadata()) { // load glyphs - OsuFile osu = focusNode.osuFiles.get(0); - Utils.loadGlyphs(Utils.FONT_LARGE, osu.titleUnicode, osu.artistUnicode); + Beatmap beatmap = focusNode.beatmaps.get(0); + Utils.loadGlyphs(Utils.FONT_LARGE, beatmap.titleUnicode, beatmap.artistUnicode); } } marginX += 5; @@ -437,14 +437,14 @@ public class SongMenu extends BasicGameState { // scroll bar if (focusNode != null) { - int focusNodes = focusNode.osuFiles.size(); - int totalNodes = OsuGroupList.get().size() + focusNodes - 1; + int focusNodes = focusNode.beatmaps.size(); + int totalNodes = BeatmapSetList.get().size() + focusNodes - 1; if (totalNodes > MAX_SONG_BUTTONS) { int startIndex = startNode.index; if (startNode.index > focusNode.index) startIndex += focusNodes; else if (startNode.index == focusNode.index) - startIndex += startNode.osuFileIndex; + startIndex += startNode.beatmapIndex; UI.drawScrollbar(g, startIndex, totalNodes, MAX_SONG_BUTTONS, width, headerY + DIVIDER_LINE_WIDTH / 2, 0, buttonOffset - DIVIDER_LINE_WIDTH * 1.5f, buttonOffset, Utils.COLOR_BLACK_ALPHA, Color.white, true); @@ -501,9 +501,9 @@ public class SongMenu extends BasicGameState { // store the start/focus nodes if (focusNode != null) - oldFocusNode = new SongNode(OsuGroupList.get().getBaseNode(focusNode.index), focusNode.osuFileIndex); + oldFocusNode = new SongNode(BeatmapSetList.get().getBaseNode(focusNode.index), focusNode.beatmapIndex); - if (OsuGroupList.get().search(search.getText())) { + if (BeatmapSetList.get().search(search.getText())) { // reset song stack randomStack = new Stack(); @@ -515,19 +515,19 @@ public class SongMenu extends BasicGameState { startNode = focusNode = null; scoreMap = null; focusScores = null; - if (OsuGroupList.get().size() > 0) { - OsuGroupList.get().init(); + if (BeatmapSetList.get().size() > 0) { + BeatmapSetList.get().init(); if (search.getText().isEmpty()) { // cleared search // use previous start/focus if possible if (oldFocusNode != null) setFocus(oldFocusNode.getNode(), oldFocusNode.getIndex(), true, true); else - setFocus(OsuGroupList.get().getRandomNode(), -1, true, true); + setFocus(BeatmapSetList.get().getRandomNode(), -1, true, true); } else { - int size = OsuGroupList.get().size(); + int size = BeatmapSetList.get().size(); searchResultString = String.format("%d match%s found!", size, (size == 1) ? "" : "es"); - setFocus(OsuGroupList.get().getRandomNode(), -1, true, true); + setFocus(BeatmapSetList.get().getRandomNode(), -1, true, true); } oldFocusNode = null; } else if (!search.getText().isEmpty()) @@ -555,9 +555,9 @@ public class SongMenu extends BasicGameState { // mouse hover boolean isHover = false; if (mouseY > headerY && mouseY < footerY) { - OsuGroupNode node = startNode; + BeatmapSetNode node = startNode; for (int i = 0; i < MAX_SONG_BUTTONS && node != null; i++, node = node.next) { - float cx = (node.index == OsuGroupList.get().getExpandedIndex()) ? buttonX * 0.9f : buttonX; + float cx = (node.index == BeatmapSetList.get().getExpandedIndex()) ? buttonX * 0.9f : buttonX; if ((mouseX > cx && mouseX < cx + buttonWidth) && (mouseY > buttonY + (i * buttonOffset) && mouseY < buttonY + (i * buttonOffset) + buttonHeight)) { if (i == hoverIndex) { @@ -641,10 +641,10 @@ public class SongMenu extends BasicGameState { if (sort != SongSort.getSort()) { SongSort.setSort(sort); SoundController.playSound(SoundEffect.MENUCLICK); - OsuGroupNode oldFocusBase = OsuGroupList.get().getBaseNode(focusNode.index); - int oldFocusFileIndex = focusNode.osuFileIndex; + BeatmapSetNode oldFocusBase = BeatmapSetList.get().getBaseNode(focusNode.index); + int oldFocusFileIndex = focusNode.beatmapIndex; focusNode = null; - OsuGroupList.get().init(); + BeatmapSetList.get().init(); setFocus(oldFocusBase, oldFocusFileIndex, true, true); } return; @@ -653,8 +653,8 @@ public class SongMenu extends BasicGameState { // song buttons if (y > headerY && y < footerY) { - int expandedIndex = OsuGroupList.get().getExpandedIndex(); - OsuGroupNode node = startNode; + int expandedIndex = BeatmapSetList.get().getExpandedIndex(); + BeatmapSetNode node = startNode; for (int i = 0; i < MAX_SONG_BUTTONS && node != null; i++, node = node.next) { // is button at this index clicked? float cx = (node.index == expandedIndex) ? buttonX * 0.9f : buttonX; @@ -665,7 +665,7 @@ public class SongMenu extends BasicGameState { // clicked node is already expanded if (node.index == expandedIndex) { - if (node.osuFileIndex == focusNode.osuFileIndex) { + if (node.beatmapIndex == focusNode.beatmapIndex) { // if already focused, load the beatmap if (button != Input.MOUSE_RIGHT_BUTTON) startGame(); @@ -730,7 +730,7 @@ public class SongMenu extends BasicGameState { switch (key) { case Input.KEY_ESCAPE: if (reloadThread != null) { - // beatmap reloading: stop parsing OsuFiles by sending interrupt to OsuParser + // beatmap reloading: stop parsing beatmaps by sending interrupt to OsuParser reloadThread.interrupt(); } else if (!search.getText().isEmpty()) { // clear search text @@ -761,8 +761,8 @@ public class SongMenu extends BasicGameState { setFocus(prev.getNode(), prev.getIndex(), true, true); } else { // random track, add previous to stack - randomStack.push(new SongNode(OsuGroupList.get().getBaseNode(focusNode.index), focusNode.osuFileIndex)); - setFocus(OsuGroupList.get().getRandomNode(), -1, true, true); + randomStack.push(new SongNode(BeatmapSetList.get().getBaseNode(focusNode.index), focusNode.beatmapIndex)); + setFocus(BeatmapSetList.get().getRandomNode(), -1, true, true); } break; case Input.KEY_F3: @@ -782,7 +782,7 @@ public class SongMenu extends BasicGameState { break; if (input.isKeyDown(Input.KEY_RSHIFT) || input.isKeyDown(Input.KEY_LSHIFT)) { SoundController.playSound(SoundEffect.MENUHIT); - MenuState ms = (focusNode.osuFileIndex == -1 || focusNode.osuFiles.size() == 1) ? + MenuState ms = (focusNode.beatmapIndex == -1 || focusNode.beatmaps.size() == 1) ? MenuState.BEATMAP_DELETE_CONFIRM : MenuState.BEATMAP_DELETE_SELECT; ((ButtonMenu) game.getState(Opsu.STATE_BUTTONMENU)).setMenuState(ms, focusNode); game.enterState(Opsu.STATE_BUTTONMENU); @@ -816,10 +816,10 @@ public class SongMenu extends BasicGameState { case Input.KEY_RIGHT: if (focusNode == null) break; - OsuGroupNode next = focusNode.next; + BeatmapSetNode next = focusNode.next; if (next != null) { SoundController.playSound(SoundEffect.MENUCLICK); - OsuGroupNode oldStartNode = startNode; + BeatmapSetNode oldStartNode = startNode; float oldHoverOffset = hoverOffset; int oldHoverIndex = hoverIndex; setFocus(next, 0, false, true); @@ -832,13 +832,13 @@ public class SongMenu extends BasicGameState { case Input.KEY_LEFT: if (focusNode == null) break; - OsuGroupNode prev = focusNode.prev; + BeatmapSetNode prev = focusNode.prev; if (prev != null) { SoundController.playSound(SoundEffect.MENUCLICK); - OsuGroupNode oldStartNode = startNode; + BeatmapSetNode oldStartNode = startNode; float oldHoverOffset = hoverOffset; int oldHoverIndex = hoverIndex; - setFocus(prev, (prev.index == focusNode.index) ? 0 : prev.osuFiles.size() - 1, false, true); + setFocus(prev, (prev.index == focusNode.index) ? 0 : prev.beatmaps.size() - 1, false, true); if (startNode == oldStartNode) { hoverOffset = oldHoverOffset; hoverIndex = oldHoverIndex; @@ -949,13 +949,13 @@ public class SongMenu extends BasicGameState { randomStack = new Stack(); // set focus node if not set (e.g. theme song playing) - if (focusNode == null && OsuGroupList.get().size() > 0) - setFocus(OsuGroupList.get().getRandomNode(), -1, true, true); + if (focusNode == null && BeatmapSetList.get().size() > 0) + setFocus(BeatmapSetList.get().getRandomNode(), -1, true, true); // reset music track else if (resetTrack) { MusicController.pause(); - MusicController.playAt(MusicController.getOsuFile().previewTime, true); + MusicController.playAt(MusicController.getBeatmap().previewTime, true); resetTrack = false; } @@ -982,7 +982,7 @@ public class SongMenu extends BasicGameState { // reload scores if (focusNode != null) { - scoreMap = ScoreDB.getMapSetScores(focusNode.osuFiles.get(focusNode.osuFileIndex)); + scoreMap = ScoreDB.getMapSetScores(focusNode.beatmaps.get(focusNode.beatmapIndex)); focusScores = getScoreDataForNode(focusNode, true); } @@ -993,31 +993,31 @@ public class SongMenu extends BasicGameState { if (stateAction != null) { switch (stateAction) { case BEATMAP: // clear all scores - if (stateActionNode == null || stateActionNode.osuFileIndex == -1) + if (stateActionNode == null || stateActionNode.beatmapIndex == -1) break; - OsuFile osu = stateActionNode.osuFiles.get(stateActionNode.osuFileIndex); - ScoreDB.deleteScore(osu); + Beatmap beatmap = stateActionNode.beatmaps.get(stateActionNode.beatmapIndex); + ScoreDB.deleteScore(beatmap); if (stateActionNode == focusNode) { focusScores = null; - scoreMap.remove(osu.version); + scoreMap.remove(beatmap.version); } break; case SCORE: // clear single score if (stateActionScore == null) break; ScoreDB.deleteScore(stateActionScore); - scoreMap = ScoreDB.getMapSetScores(focusNode.osuFiles.get(focusNode.osuFileIndex)); + scoreMap = ScoreDB.getMapSetScores(focusNode.beatmaps.get(focusNode.beatmapIndex)); focusScores = getScoreDataForNode(focusNode, true); startScore = 0; break; case BEATMAP_DELETE_CONFIRM: // delete song group if (stateActionNode == null) break; - OsuGroupNode - prev = OsuGroupList.get().getBaseNode(stateActionNode.index - 1), - next = OsuGroupList.get().getBaseNode(stateActionNode.index + 1); + BeatmapSetNode + prev = BeatmapSetList.get().getBaseNode(stateActionNode.index - 1), + next = BeatmapSetList.get().getBaseNode(stateActionNode.index + 1); int oldIndex = stateActionNode.index, focusNodeIndex = focusNode.index, startNodeIndex = startNode.index; - OsuGroupList.get().deleteSongGroup(stateActionNode); + BeatmapSetList.get().deleteSongGroup(stateActionNode); if (oldIndex == focusNodeIndex) { if (prev != null) setFocus(prev, -1, true, true); @@ -1046,7 +1046,7 @@ public class SongMenu extends BasicGameState { if (stateActionNode == null) break; int index = stateActionNode.index; - OsuGroupList.get().deleteSong(stateActionNode); + BeatmapSetList.get().deleteSong(stateActionNode); if (stateActionNode == focusNode) { if (stateActionNode.prev != null && !(stateActionNode.next != null && stateActionNode.next.index == index)) { @@ -1088,7 +1088,7 @@ public class SongMenu extends BasicGameState { @Override public void run() { // clear the beatmap cache - OsuDB.clearDatabase(); + BeatmapDB.clearDatabase(); // invoke unpacker and parser File beatmapDir = Options.getBeatmapDir(); @@ -1096,9 +1096,9 @@ public class SongMenu extends BasicGameState { OsuParser.parseAllFiles(beatmapDir); // initialize song list - if (OsuGroupList.get().size() > 0) { - OsuGroupList.get().init(); - setFocus(OsuGroupList.get().getRandomNode(), -1, true, true); + if (BeatmapSetList.get().size() > 0) { + BeatmapSetList.get().init(); + setFocus(BeatmapSetList.get().getRandomNode(), -1, true, true); } else MusicController.playThemeSong(); @@ -1146,7 +1146,7 @@ public class SongMenu extends BasicGameState { n++; shifted = true; } else if (n > 0 && startNode.next != null && - OsuGroupList.get().getNode(startNode, MAX_SONG_BUTTONS) != null) { + BeatmapSetList.get().getNode(startNode, MAX_SONG_BUTTONS) != null) { startNode = startNode.next; buttonY -= buttonOffset / 4; if (buttonY < headerY - height * 0.02f) @@ -1166,69 +1166,69 @@ public class SongMenu extends BasicGameState { /** * Sets a new focus node. * @param node the base node; it will be expanded if it isn't already - * @param osuFileIndex the OsuFile element to focus; if out of bounds, it will be randomly chosen + * @param beatmapIndex the beatmap element to focus; if out of bounds, it will be randomly chosen * @param changeStartNode if true, startNode will be set to the first node in the group * @param preview whether to start at the preview time (true) or beginning (false) * @return the old focus node */ - public OsuGroupNode setFocus(OsuGroupNode node, int osuFileIndex, boolean changeStartNode, boolean preview) { + public BeatmapSetNode setFocus(BeatmapSetNode node, int beatmapIndex, boolean changeStartNode, boolean preview) { if (node == null) return null; hoverOffset = 0f; hoverIndex = -1; songInfo = null; - OsuGroupNode oldFocus = focusNode; + BeatmapSetNode oldFocus = focusNode; // expand node before focusing it - int expandedIndex = OsuGroupList.get().getExpandedIndex(); + int expandedIndex = BeatmapSetList.get().getExpandedIndex(); if (node.index != expandedIndex) { - node = OsuGroupList.get().expand(node.index); + node = BeatmapSetList.get().expand(node.index); // if start node was previously expanded, move it if (startNode != null && startNode.index == expandedIndex) - startNode = OsuGroupList.get().getBaseNode(startNode.index); + startNode = BeatmapSetList.get().getBaseNode(startNode.index); } - // check osuFileIndex bounds - int length = node.osuFiles.size(); - if (osuFileIndex < 0 || osuFileIndex > length - 1) // set a random index - osuFileIndex = (int) (Math.random() * length); + // check beatmapIndex bounds + int length = node.beatmaps.size(); + if (beatmapIndex < 0 || beatmapIndex > length - 1) // set a random index + beatmapIndex = (int) (Math.random() * length); // change the focus node - if (changeStartNode || (startNode.index == 0 && startNode.osuFileIndex == -1 && startNode.prev == null)) + if (changeStartNode || (startNode.index == 0 && startNode.beatmapIndex == -1 && startNode.prev == null)) startNode = node; - focusNode = OsuGroupList.get().getNode(node, osuFileIndex); - OsuFile osu = focusNode.osuFiles.get(focusNode.osuFileIndex); - MusicController.play(osu, false, preview); + focusNode = BeatmapSetList.get().getNode(node, beatmapIndex); + Beatmap beatmap = focusNode.beatmaps.get(focusNode.beatmapIndex); + MusicController.play(beatmap, false, preview); // load scores - scoreMap = ScoreDB.getMapSetScores(osu); + scoreMap = ScoreDB.getMapSetScores(beatmap); focusScores = getScoreDataForNode(focusNode, true); startScore = 0; // check startNode bounds - while (startNode.index >= OsuGroupList.get().size() + length - MAX_SONG_BUTTONS && startNode.prev != null) + while (startNode.index >= BeatmapSetList.get().size() + length - MAX_SONG_BUTTONS && startNode.prev != null) startNode = startNode.prev; // make sure focusNode is on the screen (TODO: cleanup...) - int val = focusNode.index + focusNode.osuFileIndex - (startNode.index + MAX_SONG_BUTTONS) + 1; + int val = focusNode.index + focusNode.beatmapIndex - (startNode.index + MAX_SONG_BUTTONS) + 1; if (val > 0) // below screen changeIndex(val); else { // above screen if (focusNode.index == startNode.index) { - val = focusNode.index + focusNode.osuFileIndex - (startNode.index + startNode.osuFileIndex); + val = focusNode.index + focusNode.beatmapIndex - (startNode.index + startNode.beatmapIndex); if (val < 0) changeIndex(val); } else if (startNode.index > focusNode.index) { - val = focusNode.index - focusNode.osuFiles.size() + focusNode.osuFileIndex - startNode.index + 1; + val = focusNode.index - focusNode.beatmaps.size() + focusNode.beatmapIndex - startNode.index + 1; if (val < 0) changeIndex(val); } } // if start node is expanded and on group node, move it - if (startNode.index == focusNode.index && startNode.osuFileIndex == -1) + if (startNode.index == focusNode.index && startNode.beatmapIndex == -1) changeIndex(1); return oldFocus; @@ -1255,7 +1255,7 @@ public class SongMenu extends BasicGameState { * @param menuState the menu state determining the action * @param node the song node to perform the action on */ - public void doStateActionOnLoad(MenuState menuState, OsuGroupNode node) { + public void doStateActionOnLoad(MenuState menuState, BeatmapSetNode node) { doStateActionOnLoad(menuState, node, null); } @@ -1274,32 +1274,32 @@ public class SongMenu extends BasicGameState { * @param node the song node to perform the action on * @param scoreData the score data to perform the action on */ - private void doStateActionOnLoad(MenuState menuState, OsuGroupNode node, ScoreData scoreData) { + private void doStateActionOnLoad(MenuState menuState, BeatmapSetNode node, ScoreData scoreData) { stateAction = menuState; stateActionNode = node; stateActionScore = scoreData; } /** - * Returns all the score data for an OsuGroupNode from scoreMap. + * Returns all the score data for an BeatmapSetNode from scoreMap. * If no score data is available for the node, return null. - * @param node the OsuGroupNode + * @param node the BeatmapSetNode * @param setTimeSince whether or not to set the "time since" field for the scores * @return the ScoreData array */ - private ScoreData[] getScoreDataForNode(OsuGroupNode node, boolean setTimeSince) { - if (scoreMap == null || scoreMap.isEmpty() || node.osuFileIndex == -1) // node not expanded + private ScoreData[] getScoreDataForNode(BeatmapSetNode node, boolean setTimeSince) { + if (scoreMap == null || scoreMap.isEmpty() || node.beatmapIndex == -1) // node not expanded return null; - OsuFile osu = node.osuFiles.get(node.osuFileIndex); - ScoreData[] scores = scoreMap.get(osu.version); + Beatmap beatmap = node.beatmaps.get(node.beatmapIndex); + ScoreData[] scores = scoreMap.get(beatmap.version); if (scores == null || scores.length < 1) // no scores return null; ScoreData s = scores[0]; - if (osu.beatmapID == s.MID && osu.beatmapSetID == s.MSID && - osu.title.equals(s.title) && osu.artist.equals(s.artist) && - osu.creator.equals(s.creator)) { + if (beatmap.beatmapID == s.MID && beatmap.beatmapSetID == s.MSID && + beatmap.title.equals(s.title) && beatmap.artist.equals(s.artist) && + beatmap.creator.equals(s.creator)) { if (setTimeSince) { for (int i = 0; i < scores.length; i++) scores[i].getTimeSince(); @@ -1318,9 +1318,9 @@ public class SongMenu extends BasicGameState { SoundController.playSound(SoundEffect.MENUHIT); MultiClip.destroyExtraClips(); - OsuFile osu = MusicController.getOsuFile(); + Beatmap beatmap = MusicController.getBeatmap(); Game gameState = (Game) game.getState(Opsu.STATE_GAME); - gameState.loadOsuFile(osu); + gameState.loadBeatmap(beatmap); gameState.setRestart(Game.Restart.NEW); gameState.setReplay(null); game.enterState(Opsu.STATE_GAME, new FadeOutTransition(Color.black), new FadeInTransition(Color.black)); diff --git a/src/itdelatrisu/opsu/states/Splash.java b/src/itdelatrisu/opsu/states/Splash.java index 6da11d5e..a5d94ea0 100644 --- a/src/itdelatrisu/opsu/states/Splash.java +++ b/src/itdelatrisu/opsu/states/Splash.java @@ -21,13 +21,13 @@ package itdelatrisu.opsu.states; import itdelatrisu.opsu.GameImage; import itdelatrisu.opsu.Opsu; import itdelatrisu.opsu.Options; -import itdelatrisu.opsu.OsuGroupList; import itdelatrisu.opsu.OsuParser; import itdelatrisu.opsu.OszUnpacker; import itdelatrisu.opsu.UI; import itdelatrisu.opsu.Utils; import itdelatrisu.opsu.audio.MusicController; import itdelatrisu.opsu.audio.SoundController; +import itdelatrisu.opsu.beatmap.BeatmapSetList; import java.io.File; @@ -89,7 +89,7 @@ public class Splash extends BasicGameState { if (!init) { init = true; - if (OsuGroupList.get() != null) { + if (BeatmapSetList.get() != null) { // resources already loaded (from application restart) finished = true; } else { @@ -125,12 +125,12 @@ public class Splash extends BasicGameState { // change states when loading complete if (finished && alpha >= 1f) { // initialize song list - if (OsuGroupList.get().size() > 0) { - OsuGroupList.get().init(); + if (BeatmapSetList.get().size() > 0) { + BeatmapSetList.get().init(); if (Options.isThemeSongEnabled()) MusicController.playThemeSong(); else - ((SongMenu) game.getState(Opsu.STATE_SONGMENU)).setFocus(OsuGroupList.get().getRandomNode(), -1, true, true); + ((SongMenu) game.getState(Opsu.STATE_SONGMENU)).setFocus(BeatmapSetList.get().getRandomNode(), -1, true, true); } // play the theme song @@ -151,7 +151,7 @@ public class Splash extends BasicGameState { if (++escapeCount >= 3) container.exit(); - // stop parsing OsuFiles by sending interrupt to OsuParser + // stop parsing beatmaps by sending interrupt to OsuParser else if (thread != null) thread.interrupt(); }