private void captureLoop()
{
try
{
while (true)
{
int currentPos, pos2;
// Смотрим, в каком месте находится курсор записи
captureBuffer.GetCurrentPosition(out currentPos, out pos2);
// Вычисляем размер записи
int size = currentPos - readPos;
if (size < 0)
size += bufferSize;
if (size == 0) continue;
// Читаем данные в буфер
byte[] streamBuffer = new byte[size];
var stream = new MemoryStream(streamBuffer);
captureBuffer.Read(readPos, stream, size, LockFlag.None);
bool voiceDetected = false;
// Проверяем каждый семпл, смотрим громкость
int peakVolume = 0;
for (int i = 1; i < size; i += 2)
{
int sampleVolume = streamBuffer[i] * 0x100 + streamBuffer[i - 1];
if (sampleVolume > 32767) sampleVolume -= 65536; // Оно со знаком
if (sampleVolume > peakVolume) peakVolume = sampleVolume; // Вычисляем пик громкости
// Если она выше заданное громкости определения голоса...
if (Math.Abs(sampleVolume) > DetectVolume)
{
voiceDetected = true;
if (OnPeakMeter == null) break;
//break;
}
}
if (OnPeakMeter != null) OnPeakMeter(peakVolume);
// Обнаружен голос
if (voiceDetected)
{
// Если мы ещё не пишем...
if (!IsRecording)
{
if (record != null) record.Dispose();
record = new MemoryStream();
IsRecording = true;
recordTime = 0;
// Сохраняем кусочек звука, который был до этого
if (lastSample != null && lastSize > 0)
record.Write(lastSample, 0, lastSize);
}
noRecordTime = 0; // Обнуляем счётчик времени без голоса
}
else // Если в микрофоне тишина...
{
if (IsRecording) // Если при этом идёт запись
{
noRecordTime++; // Увеличиваем счётчик времени без голоса
// И если мы молчим уже достаточно долго
if (noRecordTime >= SilenceLenghtMillisecondsMaximum / 100)
{
IsRecording = false; // Прекращаем запись
// Проверяем на заданные условия
if ((recordTime >= PhraseLengthMillisecondsMinimum / 100) &&
(recordTime <= PhraseLengthMillisecondsMaximum / 100))
{
// Приостанавливаем запись
captureBuffer.Stop();
// Отправляем записанное на обработку
processRecord(record);
// Снова запускаем запись
captureBuffer.Start(true);
}
}
}
}
// Если пишем, то добавляем данные в буфер
if (IsRecording)
{
record.Write(streamBuffer, 0, size);
recordTime++;
}
else
{
// Запомиаем семпл, пригодится
lastSample = streamBuffer;
lastSize = size;
}
// Запоминаем позицию
readPos = currentPos;
Thread.Sleep(100);
}
}
catch (ThreadAbortException)
{
}
catch (Exception ex)
{
captureThread = null;
if (OnCaptureEror != null)
OnCaptureEror(ex);
}
}