标签:style class code tar ext color
1: public class SpeakLouder
2: {
3: private WavFormat _wavFormat=new WavFormat(); //文件格式
4: private byte[] _audioData; //语音数据
5: private SpeechSynthesizer _speech; //文本转语音
6: private string _pb;//文本转语音参数
7:
8: /// <summary>
9: /// 文本转语音的说话器
10: /// </summary>
11: public SpeechSynthesizer Speech
12: {
13: set { _speech = value; }
14: }
15:
16: /// <summary>
17: /// 说话器的帮助参数
18: /// </summary>
19: public string Prompt
20: {
21: set { _pb = value; }
22: }
23:
24:
25: /// <summary>
26: /// 执行播放操作
27: /// </summary>
28: /// <param name="speech">文本转语音的说话对象</param>
29: /// <param name="pb">文本转语音的speak参数</param>
30: /// <param name="scale">语音放大倍数</param>
31: public void Play(SpeechSynthesizer speech, string pb, double scale)
32: {
33: _speech = speech;
34: _pb = pb;
35: Analyze();
36: WaveScale(scale);
37: WriteWavFile();
38: }
39:
40: #region Analyze 分析音频文件
41: /// <summary>
42: /// 分析音频文件
43: /// </summary>
44: private void Analyze()
45: {
46: MemoryStream _stream = null;
47: BinaryReader br = null;
48: try
49: {
50: //构造读取流
51: _stream = new MemoryStream();
52: _speech.SetOutputToWaveStream(_stream);
53: _speech.Speak(_pb);
54:
55: br = new BinaryReader(_stream);
56:
57: _stream.Position = 22;
58: _wavFormat.Channels = br.ReadInt16();
59: _stream.Position = 24;
60: _wavFormat.SampleRate = br.ReadInt32();
61: _stream.Position = 28;
62: _wavFormat.ByteRate = br.ReadInt32();
63: _stream.Position = 34;
64: _wavFormat.BitsPerSample = br.ReadInt16();
65: _stream.Position = 44;
66: int dataByteSize = (int)(_stream.Length - 44);
67: _audioData = new byte[dataByteSize];
68: _stream.Read(_audioData, 0, dataByteSize);
69: }
70: catch (Exception ex)
71: {
72: Akloger.Error("解析刷卡语音出错:" + ex);
73: }
74: finally
75: {
76: if (br != null)
77: {
78: br.Close();
79: br.Dispose();
80: }
81: if (_stream != null)
82: {
83: _stream.Close();
84: _stream.Dispose();
85: }
86: }
87: }
88: #endregion
89:
90: #region WriteWavFile 写文件
91: /// <summary>
92: /// 写文件
93: /// </summary>
94: /// <param name="wavFormat">文件格式</param>
95: /// <param name="audioData">音频数据</param>
96: /// <param name="startIndex">audioData数组开始索引位置</param>
97: /// <param name="length">写入audioData数组长度</param>
98: private void WriteWavFile()
99: {
100: MemoryStream fs = null;
101: BinaryWriter bw = null;
102: try
103: {
104: fs = new MemoryStream();
105: bw = new BinaryWriter(fs);
106: fs.Position = 0;
107: bw.Write(new char[4] { ‘R‘, ‘I‘, ‘F‘, ‘F‘ });
108: bw.Write((int)(_audioData.Length + 44 - 8));
109: bw.Write(new char[8] { ‘W‘, ‘A‘, ‘V‘, ‘E‘, ‘f‘, ‘m‘, ‘t‘, ‘ ‘ });
110: bw.Write((int)16);
111: bw.Write((short)1);
112: bw.Write((short)_wavFormat.Channels);
113: bw.Write(_wavFormat.SampleRate);
114: bw.Write((int)(_wavFormat.SampleRate * ((_wavFormat.BitsPerSample * _wavFormat.Channels) / 8)));
115: bw.Write((short)((_wavFormat.BitsPerSample * _wavFormat.Channels) / 8));
116: bw.Write((short)_wavFormat.BitsPerSample);
117: bw.Write(new char[4] { ‘d‘, ‘a‘, ‘t‘, ‘a‘ });
118: bw.Write(_audioData.Length);
119: bw.Write(_audioData, 0, _audioData.Length);
120:
121: //播放声音
122: fs.Position = 0;
123: SoundPlayer _player = new SoundPlayer();
124: _player.Stream = null;
125: _player.Stream = fs;
126: _player.PlaySync();
127:
128:
129: }catch (Exception ex)
130: {
131: Akloger.Error("保存刷卡语音出错:" + ex);
132: }
133: finally
134: {
135: if (bw != null)
136: {
137: bw.Close();
138: bw.Dispose();
139: }
140: if (fs != null)
141: {
142: fs.Close();
143: fs.Dispose();
144: }
145: }
146: }
147: #endregion
148:
149: #region WaveScale 放大音频音量
150: /// <summary>
151: /// 放大音频音量
152: /// </summary>
153: /// <param name="scale">音量放大倍数</param>
154: private void WaveScale(double scale)
155: {
156: //总播放时间
157: // long totalTime = _wavFile.PlayTime;
158:
159: //采样位数
160: // 16 bit 纵坐标为采样系数 细化为 2^16= 65535份 16位二进制表示 [ 0000 0000 0000 0000 ]
161: // 即为2Byte (每单位时间内产生 2Byte 的音频数据)
162:
163: int byteNumPerSample = _wavFormat.BitsPerSample / 8;
164:
165: //采样频率
166: // 11025Hz 横坐标为采样频率 单位时间为: 1/11025 s
167: //单位时间内产生的的音频数据大小为 2Byte * 11025Hz * 声道数
168:
169: //字节数组 音频数据
170: byte[] audioDatas = _audioData;
171:
172:
173: // i 的值为每次衰减处理时的 字节读取位置 (索引)
174: for (int i = 0; i < audioDatas.Length; i += byteNumPerSample)
175: {
176:
177:
178: //单位时间内的字节数为1 即采用8bit采样位数 每次只需要对一个字节进行衰减
179: if (byteNumPerSample == 1)
180: {
181: //获取需要衰减的字节值
182: var audioData = (double)audioDatas[i];
183:
184: var temp = audioData * 1;
185: if (temp < -32767.5)
186: {
187: temp = -32768;
188: }
189: else if (temp > (float)32766.5)
190: {
191: temp = 32767;
192: }
193: //进行衰减线性处理
194: byte changedAudioData = (byte)temp;
195:
196: //对原来的值进行更改
197: audioDatas[i] = changedAudioData;
198: }
199: else if (byteNumPerSample == 2)
200: {
201: //16bit 量化 每单位时间产生2Byte数据 因此取 2Byte 的数据进行衰减处理
202: byte[] audioData = new byte[2];
203: Array.Copy(audioDatas, i, audioData, 0, 2);
204:
205: //单个样点幅值
206: double sample = 0;
207:
208: //转换为整数进行线性处理
209: sample = (double)BitConverter.ToInt16(audioData, 0) * scale;
210: if (sample < -32767.5)
211: {
212: sample = -32768;
213: }
214: else if (sample > (double)32766.5)
215: {
216: sample = 32767;
217: }
218: //转换为字节存储
219: byte[] buffer = BitConverter.GetBytes(Convert.ToInt16(sample));
220: if (!BitConverter.IsLittleEndian)
221: Array.Reverse(buffer);
222:
223: Array.Copy(buffer, 0, audioDatas, i, 2);
224: }
225: }
226: _audioData = audioDatas;
227: }
228: #endregion
229:
230: }
231:
232: #region WavFormat 头文件信息
233: /// <summary>
234: /// WAV 文件格式
235: /// </summary>
236: public class WavFormat
237: {
238: /// <summary>
239: /// 采样位数
240: /// </summary>
241: public int BitsPerSample;
242: /// <summary>
243: /// 声道数
244: /// </summary>
245: public int Channels;
246: /// <summary>
247: /// 采样率
248: /// </summary>
249: public int SampleRate;
250: /// <summary>
251: /// 传输速率(播放速率)
252: /// </summary>
253: public long ByteRate;
254: }
255: #endregion
标签:style class code tar ext color
原文地址:http://www.cnblogs.com/maomao999/p/3707861.html