Add the concept of a "WorkingBeatmap" and make player load beatmaps and audio from SongSelect.

This commit is contained in:
Dean Herbert 2016-10-28 14:14:45 +09:00
parent 2cdda98b47
commit feccb7286c
5 changed files with 138 additions and 28 deletions

View File

@ -46,10 +46,11 @@ public override void Reset()
Add(new Player()
{
Beatmap = new Beatmap
{
HitObjects = objects
}
Beatmap = new WorkingBeatmap(
new Beatmap
{
HitObjects = objects
})
});
}

View File

@ -0,0 +1,62 @@
//Copyright (c) 2007-2016 ppy Pty Ltd <contact@ppy.sh>.
//Licensed under the MIT Licence - https://raw.githubusercontent.com/ppy/osu/master/LICENCE
using System;
using osu.Framework.Audio.Track;
using osu.Game.Beatmaps.IO;
namespace osu.Game.Beatmaps
{
public class WorkingBeatmap : IDisposable
{
public readonly ArchiveReader Reader;
public readonly Beatmap Beatmap;
private AudioTrack track;
public AudioTrack Track
{
get
{
if (track == null)
{
var trackData = Reader.ReadFile(Beatmap.Metadata.AudioFile);
if (trackData != null)
track = new AudioTrackBass(trackData);
}
return track;
}
set { track = value; }
}
public WorkingBeatmap(Beatmap beatmap, ArchiveReader reader = null)
{
Beatmap = beatmap;
Reader = reader;
}
private bool isDisposed;
protected virtual void Dispose(bool disposing)
{
if (!isDisposed)
{
track?.Dispose();
Reader?.Dispose();
isDisposed = true;
}
}
~WorkingBeatmap()
{
Dispose(false);
}
public void Dispose()
{
Dispose(true);
GC.SuppressFinalize(this);
}
}
}

View File

@ -130,43 +130,46 @@ public ArchiveReader GetReader(BeatmapSetInfo beatmapSet)
{
return ArchiveReader.GetReader(storage, beatmapSet.Path);
}
public BeatmapSetInfo GetBeatmapSet(int id)
{
return Query<BeatmapSetInfo>().Where(s => s.BeatmapSetID == id).FirstOrDefault();
}
public WorkingBeatmap GetBeatmapData(BeatmapInfo beatmapInfo)
{
var beatmapSet = Query<BeatmapSetInfo>().Where(s => s.BeatmapSetID == beatmapInfo.BeatmapSetID).FirstOrDefault();
if (beatmapSet == null)
throw new InvalidOperationException($@"Beatmap set {beatmapInfo.BeatmapSetID} is not in the local database.");
var reader = GetReader(beatmapSet);
using (var stream = new StreamReader(reader.ReadFile(beatmapInfo.Path)))
return new WorkingBeatmap(BeatmapDecoder.GetDecoder(stream)?.Decode(stream), reader);
}
public Beatmap GetBeatmap(BeatmapInfo beatmapInfo)
{
var beatmapSet = Query<BeatmapSetInfo>()
.Where(s => s.BeatmapSetID == beatmapInfo.BeatmapSetID).FirstOrDefault();
if (beatmapSet == null)
throw new InvalidOperationException(
$@"Beatmap set {beatmapInfo.BeatmapSetID} is not in the local database.");
using (var reader = GetReader(beatmapSet))
using (var stream = new StreamReader(reader.ReadFile(beatmapInfo.Path)))
{
var decoder = BeatmapDecoder.GetDecoder(stream);
return decoder.Decode(stream);
}
using (WorkingBeatmap data = GetBeatmapData(beatmapInfo))
return data.Beatmap;
}
public TableQuery<T> Query<T>() where T : class
{
return connection.Table<T>();
}
public T GetWithChildren<T>(object id) where T : class
{
return connection.GetWithChildren<T>(id);
}
public List<T> GetAllWithChildren<T>(Expression<Func<T, bool>> filter = null,
bool recursive = true) where T : class
{
return connection.GetAllWithChildren<T>(filter, recursive);
}
public T GetChildren<T>(T item, bool recursive = true)
{
if (item == null) return default(T);

View File

@ -1,7 +1,6 @@
//Copyright (c) 2007-2016 ppy Pty Ltd <contact@ppy.sh>.
//Licensed under the MIT Licence - https://raw.githubusercontent.com/ppy/osu/master/LICENCE
using System.Collections.Generic;
using osu.Framework.Graphics;
using osu.Game.Beatmaps;
using osu.Game.Beatmaps.Objects;
@ -12,6 +11,9 @@
using osu.Game.GameModes.Play.Taiko;
using osu.Framework;
using osu.Game.Database;
using osu.Framework.Timing;
using osu.Framework.GameModes;
using osu.Framework.Audio.Track;
namespace osu.Game.GameModes.Play
{
@ -20,10 +22,29 @@ public class Player : OsuGameMode
protected override BackgroundMode CreateBackground() => new BackgroundModeCustom(@"Backgrounds/bg4");
public BeatmapInfo BeatmapInfo;
public Beatmap Beatmap;
public WorkingBeatmap Beatmap;
public PlayMode PlayMode;
protected override IFrameBasedClock Clock => playerClock;
private InterpolatingFramedClock playerClock;
private IAdjustableClock sourceClock;
protected override void Dispose(bool isDisposing)
{
Beatmap?.Dispose();
base.Dispose(isDisposing);
}
protected override bool OnExiting(GameMode next)
{
//eagerly dispose as the finalizer runs too late right now.
Beatmap?.Dispose();
return base.OnExiting(next);
}
public override void Load(BaseGame game)
{
base.Load(game);
@ -31,7 +52,7 @@ public override void Load(BaseGame game)
try
{
if (Beatmap == null)
Beatmap = ((OsuGame)game).Beatmaps.GetBeatmap(BeatmapInfo);
Beatmap = ((OsuGame)game).Beatmaps.GetBeatmapData(BeatmapInfo);
}
catch
{
@ -40,6 +61,22 @@ public override void Load(BaseGame game)
return;
}
AudioTrack track = Beatmap.Track;
if (track != null)
{
game.Audio.Track.SetExclusive(track);
sourceClock = track;
}
sourceClock = (IAdjustableClock)Beatmap.Track ?? new StopwatchClock();
playerClock = new InterpolatingFramedClock(sourceClock);
Schedule(() =>
{
sourceClock.Start();
});
HitRenderer hitRenderer;
ScoreOverlay scoreOverlay;
@ -50,7 +87,7 @@ public override void Load(BaseGame game)
hitRenderer = new OsuHitRenderer
{
Objects = Beatmap.HitObjects,
Objects = Beatmap.Beatmap.HitObjects,
Anchor = Anchor.Centre,
Origin = Anchor.Centre
};
@ -60,7 +97,7 @@ public override void Load(BaseGame game)
hitRenderer = new TaikoHitRenderer
{
Objects = Beatmap.HitObjects,
Objects = Beatmap.Beatmap.HitObjects,
Anchor = Anchor.Centre,
Origin = Anchor.Centre
};
@ -70,7 +107,7 @@ public override void Load(BaseGame game)
hitRenderer = new CatchHitRenderer
{
Objects = Beatmap.HitObjects,
Objects = Beatmap.Beatmap.HitObjects,
Anchor = Anchor.Centre,
Origin = Anchor.Centre
};
@ -80,7 +117,7 @@ public override void Load(BaseGame game)
hitRenderer = new ManiaHitRenderer
{
Objects = Beatmap.HitObjects,
Objects = Beatmap.Beatmap.HitObjects,
Anchor = Anchor.Centre,
Origin = Anchor.Centre
};
@ -96,5 +133,11 @@ public override void Load(BaseGame game)
scoreOverlay,
};
}
protected override void Update()
{
base.Update();
playerClock.ProcessFrame();
}
}
}

View File

@ -64,6 +64,7 @@
</ItemGroup>
<ItemGroup>
<Compile Include="Beatmaps\Beatmap.cs" />
<Compile Include="Beatmaps\WorkingBeatmap.cs" />
<Compile Include="Beatmaps\Drawable\BeatmapSetHeader.cs" />
<Compile Include="Beatmaps\Drawable\DifficultyIcon.cs" />
<Compile Include="Beatmaps\Drawable\Panel.cs" />