Posts Tagged ‘Codec’

HowTo: Compress speech audio using CSpeex codec at Silverlight apps

Following up on my post on how to fix CSpeex ( to compile at Silverlight 5 (see 

Initially I thought it was not working correctly, but then I noticed I was running it on Terminal Server and didn’t have an audio device available. Running SLAudioDemo included in the CSpeex distribution (after doing the fix mentioned at my post above) seems to work fine on my local PC.

The SLAudioDemo demonstrates capturing audio into memory as a compressed CSpeex stream which it can decompress and save into a .WAV file that one can play say with Windows Media Player. The WAV is uncompressed, since SLAudioDemo compresses in memory (via StreamAudioSink) and decompresses to normal PCM WAV when you save (else it would be unplayable).

Obviously the Speex codec is useful for uploading (e.g. via HSS Interlink) compressed audio to a server (or to the other end at some voice chat app) and decompress there before playback (similarly the other way around).

At the server side if you want to do audio storage too, you could also keep an extra decoded copy of the compressed Speex audio data, recoded into WMA using automation of Microsoft Expression Encoder for example (see Microsoft Transform Manager, can do this in the background if you uncompress into a .WAV file at some incoming folder). That way you could serve that audio to your Silverlight client as Speex-encoded data file, but also to other users that use Windows Media Player to get the audio file from some URL etc. Could also encode to MP4/AAC or MP3 but there are licensing issues with those from what I know.


For the CSpeex encoder see StreamAudioSink.cs. Only 2 lines are needed in MainPage.xaml.cs of SLAudioDemo:

streamAudioSink = new StreamAudioSink();
streamAudioSink.CaptureSource = _captureSource;

after you 1st declare at the top level (must have this as a top-level field, else the garbage collector can get it)

private StreamAudioSink streamAudioSink;


Here’s the decoding code that saves the WAV (from MainPage.xaml.cs):

if (sfd.ShowDialog() == true)
  // User selected item. Only property we can get to is.
  using (Stream stream = sfd.OpenFile())
    JSpeexDec decoder = new JSpeexDec();
    Stream memStream = streamAudioSink.MemFile.InnerStream;
    memStream.Position = 0;
    decoder.decode(new RandomInputStream(memStream), 
new RandomOutputStream(stream)); stream.Close(); } }


Don’t get puzzled by the use of RandomInputStream / RandomOutputStream. These are from Java’s I/O package (*) that CSpeex has ported to .NET, since it’s in fact a port of JSpeex, a Java implementation of the Speex codec.

Fix: compile CSpeex audio codec at Silverlight 4 RC+ and Silverlight 5

Just added an issue to CSpeex project – – with some fixes to make it compile for Silverlight 4 RC and higher (was for Silverlight 4 Beta).

1) at "MainPage.xaml.cs", replace with this method implementation:

private void TakeSnapshot_Click(object sender, RoutedEventArgs e)
  if (_captureSource != null)
    // capture the current frame and add it to our observable collection
    _captureSource.CaptureImageCompleted += (source, eventargs) =>

  //”ImageCaptureAsync" method replaced by "CaptureImageAsync" at Silverlight 4 RC


2) at "StreamAudioSync.cs" do this small change:

protected override void OnFormatChange(AudioFormat audioFormat)
  if (audioFormat.WaveFormat == WaveFormatType.Pcm)

  //”PCM" renamed to "Pcm" at Silverlight 4 RC (after SL4beta)



Note that the CSpeex-SL project won’t load if you don’t have Silverlight 3 SDK installed. After loading you can open up properties of that project and of SLAudioDemo one and set the target to Silverlight 5 from Silverlight 3, then save those two projects and rebuild the solution.

%d bloggers like this: