ABStemPlayer/AudioCore_Tests/StemDecoder_Tests.cs

148 lines
4.7 KiB
C#

using AudioCore.Impl;
using AudioCore.Models;
namespace AudioCore_Tests;
[TestClass]
public sealed class StemDecoder_Tests
{
[TestMethod]
public async Task DecodeNextBlockAsync_ReturnsBlock()
{
var pool = new AudioBufferPool();
var samples = Enumerable.Range(0, 48000).Select(i => (float)i).ToArray();
var reader = new FakeAudioReader(samples, 48000, 2);
var stem = new StemTrack { Name = "test", FilePath = "file.wav" };
var decoder = new StemDecoder(reader, pool, stem, blockSize: 1024);
var nullableBlock = await decoder.DecodeNextBlockAsync(CancellationToken.None);
Assert.IsNotNull(nullableBlock);
var block = nullableBlock.Value;
Assert.AreEqual(1024, block.Frames);
Assert.AreEqual(0, block.Position);
Assert.AreEqual(48000, block.SampleRate);
Assert.AreEqual(2, block.Channels);
block.Dispose();
}
[TestMethod]
public async Task DecodeNextBlockAsync_AdvancesPosition()
{
var pool = new AudioBufferPool();
var samples = Enumerable.Range(0, 48000).Select(i => (float)i).ToArray();
var reader = new FakeAudioReader(samples);
var stem = new StemTrack { Name = "test", FilePath = "file.wav" };
var decoder = new StemDecoder(reader, pool, stem, blockSize: 1000);
var b1 = await decoder.DecodeNextBlockAsync(CancellationToken.None);
var b2 = await decoder.DecodeNextBlockAsync(CancellationToken.None);
Assert.IsNotNull(b1);
Assert.IsNotNull(b2);
Assert.AreEqual(0, b1!.Value.Position);
Assert.AreEqual(1000, b2!.Value.Position);
b1.Value.Dispose();
b2.Value.Dispose();
}
[TestMethod]
public async Task Seek_MovesReaderAndDecoderPosition()
{
var pool = new AudioBufferPool();
var samples = Enumerable.Range(0, 48000).Select(i => (float)i).ToArray();
var reader = new FakeAudioReader(samples);
var stem = new StemTrack { Name = "test", FilePath = "file.wav" };
var decoder = new StemDecoder(reader, pool, stem, blockSize: 500);
decoder.Seek(2000);
var block = await decoder.DecodeNextBlockAsync(CancellationToken.None);
Assert.IsNotNull(block);
Assert.AreEqual(2000, block!.Value.Position);
Assert.AreEqual(500, block.Value.Frames);
block.Value.Dispose();
}
[TestMethod]
public async Task Reset_ReturnsToStart()
{
var pool = new AudioBufferPool();
var samples = Enumerable.Range(0, 48000).Select(i => (float)i).ToArray();
var reader = new FakeAudioReader(samples);
var stem = new StemTrack { Name = "test", FilePath = "file.wav" };
var decoder = new StemDecoder(reader, pool, stem, blockSize: 500);
var b1 = await decoder.DecodeNextBlockAsync(CancellationToken.None);
decoder.Reset();
var b2 = await decoder.DecodeNextBlockAsync(CancellationToken.None);
Assert.IsNotNull(b2);
Assert.AreEqual(0, b2!.Value.Position);
b1!.Value.Dispose();
b2!.Value.Dispose();
}
[TestMethod]
public async Task DecodeNextBlockAsync_ReturnsNullAtEnd()
{
var pool = new AudioBufferPool();
var samples = new float[2000];
var reader = new FakeAudioReader(samples, 48000, 2);
var stem = new StemTrack { Name = "test", FilePath = "file.wav" };
var decoder = new StemDecoder(reader, pool, stem, blockSize: 1024);
var b1 = await decoder.DecodeNextBlockAsync(CancellationToken.None);
Assert.IsNotNull(b1);
b1!.Value.Dispose();
var b2 = await decoder.DecodeNextBlockAsync(CancellationToken.None);
if (b2 != null)
b2!.Value.Dispose();
var b3 = await decoder.DecodeNextBlockAsync(CancellationToken.None);
Assert.IsNull(b3, "Decoder should return null at end of stream");
}
[TestMethod]
public void Dispose_DisposesReader()
{
var pool = new AudioBufferPool();
var samples = new float[1000];
var reader = new FakeAudioReader(samples);
var stem = new StemTrack { Name = "test", FilePath = "file.wav" };
var decoder = new StemDecoder(reader, pool, stem);
decoder.Dispose();
try
{
// FakeAudioReader throws ObjectDisposedException when used after Dispose
var _ = reader.ReadAsync(new float[10].AsMemory(), CancellationToken.None).Result;
Assert.Fail("Expected ObjectDisposedException");
}
catch (AssertFailedException)
{
throw;
}
catch (Exception ex)
{
Assert.IsInstanceOfType(ex, typeof(ObjectDisposedException));
}
}
}