Refactoring codecs infrastructure:

AudioWriterSettings passed to IAdioDest constructors now
AudioWriterSettings now includes AudioPCMConfig
This commit is contained in:
Grigory Chudov
2013-04-07 20:41:58 -04:00
parent b44e482dee
commit 9670c6c891
43 changed files with 652 additions and 723 deletions

View File

@@ -327,7 +327,7 @@ namespace CUETools.Codecs
public void Prepare(IAudioDest dest)
{
if (dest.PCM.ChannelCount != pcm.ChannelCount || dest.PCM.BitsPerSample != pcm.BitsPerSample)
if (dest.Settings.PCM.ChannelCount != pcm.ChannelCount || dest.Settings.PCM.BitsPerSample != pcm.BitsPerSample)
throw new Exception("AudioBuffer format mismatch");
}

View File

@@ -9,12 +9,14 @@ namespace CUETools.Codecs
public class AudioEncoderSettings
{
public AudioEncoderSettings()
: this("", "")
{
// Iterate through each property and call ResetValue()
foreach (PropertyDescriptor property in TypeDescriptor.GetProperties(this))
property.ResetValue(this);
this.m_supported_modes = "";
this.EncoderMode = "";
}
public AudioEncoderSettings(AudioPCMConfig pcm)
: this("", "")
{
this.PCM = pcm;
}
public AudioEncoderSettings(string supported_modes, string default_mode)
@@ -38,24 +40,36 @@ namespace CUETools.Codecs
return BlockSize == 0 && Padding >= 0;
}
public T Clone<T>() where T : AudioEncoderSettings
public void Validate()
{
if (this as T == null)
throw new Exception("Unsupported options " + this);
var result = this.MemberwiseClone() as T;
if (!result.IsValid())
if (!IsValid())
throw new Exception("unsupported encoder settings");
return result;
}
public AudioEncoderSettings Clone()
{
return this.MemberwiseClone() as AudioEncoderSettings;
}
[Browsable(false)]
[XmlIgnore]
public AudioPCMConfig PCM
{
get;
set;
}
[Browsable(false)]
[DefaultValue(0)]
public int BlockSize
{
get; set;
get;
set;
}
[Browsable(false)]
[XmlIgnore]
[DefaultValue(4096)]
public int Padding
{
@@ -64,6 +78,7 @@ namespace CUETools.Codecs
}
[Browsable(false)]
[DefaultValue("")]
public string EncoderMode
{
get;

View File

@@ -94,6 +94,7 @@
<Compile Include="UserDefinedWriter.cs" />
<Compile Include="WAVReader.cs" />
<Compile Include="WAVWriter.cs" />
<Compile Include="WAVWriterSettings.cs" />
</ItemGroup>
<ItemGroup>
<BootstrapperPackage Include="Microsoft.Net.Client.3.5">

View File

@@ -4,11 +4,11 @@ namespace CUETools.Codecs
{
public class DummyWriter : IAudioDest
{
AudioPCMConfig _pcm;
AudioEncoderSettings m_settings;
public DummyWriter(string path, AudioPCMConfig pcm)
public DummyWriter(string path, AudioEncoderSettings settings)
{
_pcm = pcm;
m_settings = settings;
}
public void Close()
@@ -28,18 +28,8 @@ namespace CUETools.Codecs
{
get
{
return new AudioEncoderSettings();
return m_settings;
}
set
{
if (value != null && value.GetType() != typeof(AudioEncoderSettings))
throw new Exception("Unsupported options " + value);
}
}
public AudioPCMConfig PCM
{
get { return _pcm; }
}
public void Write(AudioBuffer buff)

View File

@@ -2,11 +2,10 @@
{
public interface IAudioDest
{
AudioPCMConfig PCM { get; }
string Path { get; }
AudioEncoderSettings Settings { get; set; }
long FinalSampleCount { set; }
AudioEncoderSettings Settings { get; }
string Path { get; }
long FinalSampleCount { set; }
void Write(AudioBuffer buffer);
void Close();

View File

@@ -14,6 +14,7 @@ namespace CUETools.Codecs
string tempFile = null;
long _finalSampleCount = -1;
bool closed = false;
private AudioEncoderSettings m_settings;
public long Position
{
@@ -29,29 +30,19 @@ namespace CUETools.Codecs
}
// !!!! Must not start the process in constructor, so that we can set CompressionLevel via Settings!
private AudioEncoderSettings m_settings = new AudioEncoderSettings();
public AudioEncoderSettings Settings
{
get
{
return m_settings;
}
set
{
m_settings = value.Clone<AudioEncoderSettings>();
}
}
public AudioPCMConfig PCM
{
get { return wrt.PCM; }
}
public string Path { get { return _path; } }
public UserDefinedWriter(string path, Stream IO, AudioPCMConfig pcm, string encoder, string encoderParams, string encoderMode, int padding)
public UserDefinedWriter(string path, Stream IO, AudioEncoderSettings settings, string encoder, string encoderParams, string encoderMode, int padding)
{
m_settings = settings as AudioEncoderSettings;
_path = path;
_encoder = encoder;
_encoderParams = encoderParams;
@@ -70,7 +61,7 @@ namespace CUETools.Codecs
_encoderProcess.StartInfo.RedirectStandardOutput = true;
if (useTempFile)
{
wrt = new WAVWriter(tempFile, null, pcm);
wrt = new WAVWriter(tempFile, null, new WAVWriterSettings(settings.PCM));
return;
}
bool started = false;
@@ -93,7 +84,7 @@ namespace CUETools.Codecs
outputBuffer = new CyclicBuffer(2 * 1024 * 1024, _encoderProcess.StandardOutput.BaseStream, outputStream);
}
Stream inputStream = new CyclicBufferOutputStream(_encoderProcess.StandardInput.BaseStream, 128 * 1024);
wrt = new WAVWriter(path, inputStream, pcm);
wrt = new WAVWriter(path, inputStream, new WAVWriterSettings(settings.PCM));
}
public void Close()

View File

@@ -4,12 +4,11 @@ using System.IO;
namespace CUETools.Codecs
{
[AudioEncoderClass("cuetools", "wav", true, 10, typeof(AudioEncoderSettings))]
[AudioEncoderClass("cuetools", "wav", true, 10, typeof(WAVWriterSettings))]
public class WAVWriter : IAudioDest
{
private Stream _IO;
private BinaryWriter _bw;
private AudioPCMConfig _pcm;
private long _sampleLen;
private string _path;
private long hdrLen = 0;
@@ -17,6 +16,7 @@ namespace CUETools.Codecs
private long _finalSampleCount = -1;
private List<byte[]> _chunks = null;
private List<uint> _chunkFCCs = null;
private WAVWriterSettings m_settings;
public long Position
{
@@ -35,32 +35,22 @@ namespace CUETools.Codecs
{
get
{
return new AudioEncoderSettings();
return m_settings;
}
set
{
if (value != null && value.GetType() != typeof(AudioEncoderSettings))
throw new Exception("Unsupported options " + value);
}
}
public AudioPCMConfig PCM
{
get { return _pcm; }
}
public string Path { get { return _path; } }
public WAVWriter(string path, Stream IO, AudioPCMConfig pcm)
public WAVWriter(string path, Stream IO, WAVWriterSettings settings)
{
_pcm = pcm;
m_settings = settings;
_path = path;
_IO = IO != null ? IO : new FileStream(path, FileMode.Create, FileAccess.Write, FileShare.Read);
_bw = new BinaryWriter(_IO);
}
public WAVWriter(string path, AudioPCMConfig pcm)
: this(path, null, pcm)
public WAVWriter(string path, WAVWriterSettings settings)
: this(path, null, settings)
{
}
@@ -85,11 +75,11 @@ namespace CUETools.Codecs
const uint fccFormat = 0x20746D66;
const uint fccData = 0x61746164;
bool wavex = _pcm.BitsPerSample != 16 && _pcm.BitsPerSample != 24;
bool wavex = Settings.PCM.BitsPerSample != 16 && Settings.PCM.BitsPerSample != 24;
hdrLen += 36 + (wavex ? 24 : 0) + 8;
uint dataLen = (uint)(_finalSampleCount * _pcm.BlockAlign);
uint dataLen = (uint)(_finalSampleCount * Settings.PCM.BlockAlign);
uint dataLenPadded = dataLen + (dataLen & 1);
_bw.Write(fccRIFF);
@@ -106,15 +96,15 @@ namespace CUETools.Codecs
_bw.Write((uint)16);
_bw.Write((ushort)1); // PCM
}
_bw.Write((ushort)_pcm.ChannelCount);
_bw.Write((uint)_pcm.SampleRate);
_bw.Write((uint)(_pcm.SampleRate * _pcm.BlockAlign));
_bw.Write((ushort)_pcm.BlockAlign);
_bw.Write((ushort)((_pcm.BitsPerSample + 7) / 8 * 8));
_bw.Write((ushort)Settings.PCM.ChannelCount);
_bw.Write((uint)Settings.PCM.SampleRate);
_bw.Write((uint)(Settings.PCM.SampleRate * Settings.PCM.BlockAlign));
_bw.Write((ushort)Settings.PCM.BlockAlign);
_bw.Write((ushort)((Settings.PCM.BitsPerSample + 7) / 8 * 8));
if (wavex)
{
_bw.Write((ushort)22); // length of WAVEX structure
_bw.Write((ushort)_pcm.BitsPerSample);
_bw.Write((ushort)Settings.PCM.BitsPerSample);
_bw.Write((uint)3); // speaker positions (3 == stereo)
_bw.Write((ushort)1); // PCM
_bw.Write((ushort)0);
@@ -150,11 +140,11 @@ namespace CUETools.Codecs
if (_finalSampleCount <= 0)
{
const long maxFileSize = 0x7FFFFFFEL;
long dataLen = _sampleLen * _pcm.BlockAlign;
long dataLen = _sampleLen * Settings.PCM.BlockAlign;
if ((dataLen & 1) == 1)
_bw.Write((byte)0);
if (dataLen + hdrLen > maxFileSize)
dataLen = ((maxFileSize - hdrLen) / _pcm.BlockAlign) * _pcm.BlockAlign;
dataLen = ((maxFileSize - hdrLen) / Settings.PCM.BlockAlign) * Settings.PCM.BlockAlign;
long dataLenPadded = dataLen + (dataLen & 1);
_bw.Seek(4, SeekOrigin.Begin);

View File

@@ -0,0 +1,19 @@
using System;
using System.Collections.Generic;
using System.Text;
namespace CUETools.Codecs
{
public class WAVWriterSettings : AudioEncoderSettings
{
public WAVWriterSettings()
: this(null)
{
}
public WAVWriterSettings(AudioPCMConfig pcm)
: base(pcm)
{
}
}
}