136 lines
5.3 KiB
C#
136 lines
5.3 KiB
C#
using FluentAssertions;
|
|
using Vav1Player.Video;
|
|
using Vav1Player.Decoder;
|
|
using Vav1Player.Rendering;
|
|
using System.Windows.Controls;
|
|
|
|
namespace Vav1Player.Tests.Integration;
|
|
|
|
public class FullVideoPlaybackIntegrationTests
|
|
{
|
|
[Fact]
|
|
public async Task VideoPlayer_WithSampleMp4_ShouldLoadSuccessfully()
|
|
{
|
|
// Arrange
|
|
var sampleFilePath = Path.Combine("..", "..", "..", "..", "sample", "output.mp4");
|
|
|
|
// Skip test if sample file doesn't exist
|
|
if (!File.Exists(sampleFilePath))
|
|
{
|
|
return; // Skip test
|
|
}
|
|
|
|
// Act & Assert
|
|
var action = async () =>
|
|
{
|
|
using var decoder = new Dav1dDecoder();
|
|
decoder.Initialize().Should().BeTrue("Decoder should initialize successfully");
|
|
|
|
// Note: We can't create WpfVideoRenderer without WPF context in unit tests
|
|
|
|
// We can't create WpfVideoRenderer without WPF context, but we can test the VideoPlayer creation
|
|
// and verify that it would work with proper renderer
|
|
var loadTest = async () =>
|
|
{
|
|
using var fileReader = new VideoFileReader(sampleFilePath);
|
|
|
|
// Verify file loads correctly
|
|
fileReader.TrackInfo.Should().NotBeNull();
|
|
fileReader.TrackInfo!.CodecType.Should().Be("av01");
|
|
fileReader.TotalSamples.Should().BeGreaterThan(0);
|
|
|
|
System.Diagnostics.Debug.WriteLine($"Loaded video: {fileReader.TrackInfo.Width}x{fileReader.TrackInfo.Height}, " +
|
|
$"{fileReader.TrackInfo.Duration:F2}s, {fileReader.TrackInfo.EstimatedFrameRate:F2} FPS, " +
|
|
$"{fileReader.TotalSamples} samples");
|
|
|
|
// Test reading and decoding first few frames
|
|
int decodedFrames = 0;
|
|
for (int i = 0; i < Math.Min(5, fileReader.TotalSamples); i++)
|
|
{
|
|
var chunk = await fileReader.ReadNextChunkAsync();
|
|
if (chunk == null) break;
|
|
|
|
var obuList = Vav1Player.Container.Av1BitstreamParser.ParseMp4Sample(chunk.Data);
|
|
if (obuList.Count > 0)
|
|
{
|
|
var combinedData = Vav1Player.Container.Av1BitstreamParser.CombineOBUs(obuList);
|
|
var decodeResult = decoder.DecodeFrame(combinedData, out var frame);
|
|
|
|
if (decodeResult && frame.HasValue)
|
|
{
|
|
decodedFrames++;
|
|
var decodedFrame = frame.Value;
|
|
System.Diagnostics.Debug.WriteLine($"Successfully decoded frame #{decodedFrames}: {decodedFrame.Width}x{decodedFrame.Height}");
|
|
decodedFrame.Release();
|
|
}
|
|
}
|
|
}
|
|
|
|
System.Diagnostics.Debug.WriteLine($"Successfully decoded {decodedFrames} frames from video file");
|
|
};
|
|
|
|
await loadTest.Should().NotThrowAsync();
|
|
};
|
|
|
|
await action.Should().NotThrowAsync();
|
|
}
|
|
|
|
[Fact]
|
|
public void FrameBuffer_ShouldBufferFramesCorrectly()
|
|
{
|
|
// Test the frame buffering system
|
|
using var frameBuffer = new FrameBuffer(maxBufferSizeMs: 500, maxFrameCount: 30);
|
|
|
|
// Verify initial state
|
|
frameBuffer.Count.Should().Be(0);
|
|
frameBuffer.IsEndOfStream.Should().BeFalse();
|
|
|
|
// Test buffer stats
|
|
var stats = frameBuffer.GetStats();
|
|
stats.FrameCount.Should().Be(0);
|
|
stats.MaxBufferMs.Should().Be(500);
|
|
stats.MaxFrameCount.Should().Be(30);
|
|
stats.BufferUtilization.Should().Be(0.0);
|
|
}
|
|
|
|
[Fact]
|
|
public async Task VideoDecoderPipeline_ShouldProcessVideoData()
|
|
{
|
|
// Arrange
|
|
var sampleFilePath = Path.Combine("..", "..", "..", "..", "sample", "output.mp4");
|
|
|
|
// Skip test if sample file doesn't exist
|
|
if (!File.Exists(sampleFilePath))
|
|
{
|
|
return; // Skip test
|
|
}
|
|
|
|
// Act & Assert
|
|
var action = async () =>
|
|
{
|
|
using var fileReader = new VideoFileReader(sampleFilePath);
|
|
using var decoder = new Dav1dDecoder();
|
|
using var frameBuffer = new FrameBuffer(maxBufferSizeMs: 500, maxFrameCount: 30);
|
|
|
|
decoder.Initialize().Should().BeTrue("Decoder should initialize successfully");
|
|
|
|
// Create decoder pipeline
|
|
using var decoderPipeline = new VideoDecoderPipeline(fileReader, decoder, frameBuffer);
|
|
|
|
// Wait a bit for initial decoding
|
|
await Task.Delay(1000);
|
|
|
|
// Check if frames were decoded and buffered
|
|
var bufferStats = frameBuffer.GetStats();
|
|
System.Diagnostics.Debug.WriteLine($"Buffer stats after 1 second: {bufferStats}");
|
|
System.Diagnostics.Debug.WriteLine($"Decoder pipeline running: {decoderPipeline.IsRunning}");
|
|
System.Diagnostics.Debug.WriteLine($"Decoded frame count: {decoderPipeline.DecodedFrameCount}");
|
|
|
|
// At least some progress should have been made
|
|
// Note: We can't guarantee frames will be decoded immediately due to timing
|
|
decoderPipeline.IsRunning.Should().BeTrue("Decoder pipeline should be running");
|
|
};
|
|
|
|
await action.Should().NotThrowAsync();
|
|
}
|
|
} |