116 lines
2.8 KiB
C#
116 lines
2.8 KiB
C#
using System.Collections.Generic;
|
|
using System.Threading;
|
|
|
|
//-----------------------------------------------------------------------------
|
|
// Copyright 2012-2021 RenderHeads Ltd. All rights reserved.
|
|
//-----------------------------------------------------------------------------
|
|
|
|
namespace RenderHeads.Media.AVProMovieCapture
|
|
{
|
|
/// Allows the user to monitor a capture that has completed, but the file is still being written to asynchronously
|
|
public class FileWritingHandler : System.IDisposable
|
|
{
|
|
private string _path;
|
|
private int _handle;
|
|
private bool _deleteFile;
|
|
private OutputTarget _outputTarget;
|
|
private VideoEncoderHints _videoEncodingHints;
|
|
private ManualResetEvent _postProcessEvent;
|
|
|
|
public string Path
|
|
{
|
|
get { return _path; }
|
|
}
|
|
|
|
internal FileWritingHandler(OutputTarget outputTarget, string path, int handle, bool deleteFile)
|
|
{
|
|
_outputTarget = outputTarget;
|
|
_path = path;
|
|
_handle = handle;
|
|
_deleteFile = deleteFile;
|
|
}
|
|
|
|
internal void AddPostOperation(VideoEncoderHints videoEncodingHints)
|
|
{
|
|
_videoEncodingHints = videoEncodingHints;
|
|
}
|
|
|
|
private bool StartPostProcess()
|
|
{
|
|
UnityEngine.Debug.Assert(_postProcessEvent == null);
|
|
if (_videoEncodingHints.allowFastStartStreamingPostProcess)
|
|
{
|
|
_postProcessEvent = MP4FileProcessing.ApplyFastStartAsync(_path, false);
|
|
if (_postProcessEvent == null)
|
|
{
|
|
UnityEngine.Debug.LogWarning("[AVProMovieCapture] failed moving atom 'moov' to start of file for fast streaming");
|
|
}
|
|
}
|
|
return true;
|
|
}
|
|
|
|
public bool IsFileReady()
|
|
{
|
|
bool result = true;
|
|
if (_handle >= 0)
|
|
{
|
|
result = NativePlugin.IsFileWritingComplete(_handle);
|
|
if (result)
|
|
{
|
|
if (_videoEncodingHints != null)
|
|
{
|
|
result = StartPostProcess();
|
|
_videoEncodingHints = null;
|
|
}
|
|
if (_postProcessEvent != null)
|
|
{
|
|
result = _postProcessEvent.WaitOne(1);
|
|
}
|
|
if (result)
|
|
{
|
|
Dispose();
|
|
}
|
|
}
|
|
}
|
|
return result;
|
|
}
|
|
|
|
public void Dispose()
|
|
{
|
|
if (_handle >= 0)
|
|
{
|
|
NativePlugin.FreeRecorder(_handle);
|
|
_handle = -1;
|
|
|
|
// Issue the free resources plugin event
|
|
NativePlugin.RenderThreadEvent(NativePlugin.PluginEvent.FreeResources, -1);
|
|
|
|
if (_deleteFile)
|
|
{
|
|
CaptureBase.DeleteCapture(_outputTarget, _path);
|
|
}
|
|
}
|
|
|
|
_videoEncodingHints = null;
|
|
_postProcessEvent = null;
|
|
}
|
|
|
|
// Helper method for cleaning up a list
|
|
// TODO: add an optional System.Action callback for each time the file writer completes
|
|
public static bool Cleanup(List<FileWritingHandler> list)
|
|
{
|
|
bool anyRemoved = false;
|
|
// NOTE: We iterate in reverse order as we're removing elements from the list
|
|
for (int i = list.Count - 1; i >= 0; i--)
|
|
{
|
|
FileWritingHandler handler = list[i];
|
|
if (handler.IsFileReady())
|
|
{
|
|
list.RemoveAt(i);
|
|
anyRemoved = true;
|
|
}
|
|
}
|
|
return anyRemoved;
|
|
}
|
|
}
|
|
} |