123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229 |
- using NAudio.CoreAudioApi;
- using NAudio.Wave;
- using System;
- using System.Collections.Generic;
- using System.IO;
- using System.Linq;
- using System.Text;
- using System.Threading;
- using System.Threading.Tasks;
- namespace AudioRecorder
- {
- public class AudioRecorder
- {
- private const string _fileExtension = ".wav";
- /// <summary>
- /// 录音(wav格式)
- /// </summary>
- private static WaveInEvent _recorder;
- /// <summary>
- /// 文件名
- /// </summary>
- private static string _fileName;
- /// <summary>
- /// 流写入文件
- /// </summary>
- private static WaveFileWriter _writer;
- /// <summary>
- /// 信号量,用于解决关闭录音时线程占用文件
- /// </summary>
- private static ManualResetEvent _manualResetEvent;
- private static AudioRecorder _instance;
- public static AudioRecorder Instance
- {
- get
- {
- if (_instance == null)
- {
- _instance = new AudioRecorder();
- }
- return _instance;
- }
- }
- /// <summary>
- /// 开启录音
- /// </summary>
- public void Start(string localAudioCachePath)
- {
- try
- {
- _recorder = new WaveInEvent();
- _recorder.DeviceNumber = 0;
- _recorder.WaveFormat = new WaveFormat(16000, 16, 1);
- _fileName = Guid.NewGuid().ToString() + _fileExtension;
- if (!Directory.Exists(localAudioCachePath))
- {
- Directory.CreateDirectory(localAudioCachePath);
- }
- _writer = new WaveFileWriter(Path.Combine(localAudioCachePath, _fileName), _recorder.WaveFormat);
- // 当有音频数据时写入器将其写入流
- _recorder.DataAvailable += (s, e) =>
- {
- _writer.Write(e.Buffer, 0, e.BytesRecorded);
- };
- // 当录音停止时关闭写入器
- _recorder.RecordingStopped += (s, e) =>
- {
- _writer.Close();
- _manualResetEvent.Set();
- };
- _recorder.StartRecording();
- }
- catch (Exception ex)
- {
- throw ex;
- }
- }
- /// <summary>
- /// 结束录音
- /// </summary>
- public string Stop(string localAudioCachePath)
- {
- try
- {
- _manualResetEvent = new ManualResetEvent(false);
- _recorder.StopRecording();
- _manualResetEvent.WaitOne(2000);
- var filePath = Path.Combine(localAudioCachePath, _fileName);
- if (!File.Exists(filePath))
- {
- return string.Empty;
- }
- // 将录音数据转为base64
- var buffer = File.ReadAllBytes(filePath);
- var base64 = Convert.ToBase64String(buffer);
- return base64;
- }
- catch (Exception ex)
- {
- throw ex;
- }
- return string.Empty;
- }
- public float GetAudioDeviceVolume(AudioDeviceTypeEnum audioTypeEnum, Action<string> logger)
- {
- try
- {
- var audioEnumerator = new MMDeviceEnumerator();
- if (audioTypeEnum == AudioDeviceTypeEnum.Mic)
- {
- var microphone = audioEnumerator.GetDefaultAudioEndpoint(DataFlow.Capture, Role.Communications);
- if (microphone != null)
- {
- return microphone.AudioEndpointVolume.MasterVolumeLevelScalar;
- }
- }
- else
- {
- var speaker = audioEnumerator.GetDefaultAudioEndpoint(DataFlow.Render, Role.Multimedia);
- if (speaker != null)
- {
- return speaker.AudioEndpointVolume.MasterVolumeLevelScalar;
- }
- }
- return 0;
- }
- catch (Exception ex)
- {
- logger("Get device default volume ex:" + ex.ToString());
- return 0;
- }
- }
- public List<string> GetAudioDevices(AudioDeviceTypeEnum audioTypeEnum)
- {
- var audioEnumerator = new MMDeviceEnumerator();
- var devices = audioEnumerator.EnumerateAudioEndPoints(audioTypeEnum == AudioDeviceTypeEnum.Speaker ?
- DataFlow.Render : DataFlow.Capture, DeviceState.Active);
- if (devices == null)
- {
- return new List<string>();
- }
- return devices.Select(x => x.FriendlyName).ToList();
- }
- public bool SetSystemAudioDevice(string deviceName)
- {
- var audioEnumerator = new MMDeviceEnumerator();
- var devices = audioEnumerator.EnumerateAudioEndPoints(DataFlow.All, DeviceState.Active);
- var selectedDevice = devices.FirstOrDefault(device => device.FriendlyName == deviceName);
- if (selectedDevice != null)
- {
- // AudioDeviceManager.SetDefaultAudioDevice(deviceName, true);
- return true;
- }
- else
- {
- return false;
- }
- }
- /// <summary>
- /// 调整声音设备音量
- /// </summary>
- /// <param name="audioTypeEnum"></param>
- /// <param name="volume"></param>
- /// <param name="logger"></param>
- public void AdjustAudioDevice(AudioDeviceTypeEnum audioTypeEnum, double volume, Action<string> logger)
- {
- var audioEnumerator = new MMDeviceEnumerator();
- var microphone = audioEnumerator.GetDefaultAudioEndpoint(DataFlow.Capture, Role.Communications);
- var speaker = audioEnumerator.GetDefaultAudioEndpoint(DataFlow.Render, Role.Multimedia);
- if (volume < 0 || volume > 1)
- {
- logger($"Invalid volum {volume}");
- return;
- }
- // 设置音量大小 (0.0f 到 1.0f)
- float micVolume = (float)volume; // 50% 音量
- float speakerVolume = (float)volume; // 75% 音量
- if (audioTypeEnum == AudioDeviceTypeEnum.Mic)
- {
- // 设置麦克风音量
- if (microphone.AudioEndpointVolume != null)
- {
- microphone.AudioEndpointVolume.MasterVolumeLevelScalar = micVolume;
- }
- }
- if (audioTypeEnum == AudioDeviceTypeEnum.Speaker)
- {
- // 设置扬声器音量
- if (speaker.AudioEndpointVolume != null)
- {
- speaker.AudioEndpointVolume.MasterVolumeLevelScalar = speakerVolume;
- }
- }
- }
- }
- public enum AudioDeviceTypeEnum
- {
- /// <summary>
- /// 麦克风
- /// </summary>
- Mic,
- /// <summary>
- /// 扬声器
- /// </summary>
- Speaker,
- }
- }
|