Skip to content

Instantly share code, notes, and snippets.

@cliftonm
Created December 23, 2016 16:45
Show Gist options
  • Star 2 You must be signed in to star a gist
  • Fork 0 You must be signed in to fork a gist
  • Save cliftonm/0052163d701db8d37393216353bf6dba to your computer and use it in GitHub Desktop.
Save cliftonm/0052163d701db8d37393216353bf6dba to your computer and use it in GitHub Desktop.
A Simple C# WinForm Sound Player Demo
using System;
using System.Drawing;
using System.IO;
using System.Windows.Forms;
using System.Media;
class BeepSample
{
static Form form;
static Button btnPlay;
static TrackBar tbFreq;
static bool playing;
static SoundPlayer player = new SoundPlayer();
static void Main()
{
Application.EnableVisualStyles();
Application.SetCompatibleTextRenderingDefault(false);
CreateUI();
WireUpButtonEvent();
WireUpTrackbarEvent();
form.ShowDialog();
player.Stop();
}
public static void CreateUI()
{
form = new Form();
form.Size = new Size(320, 150);
btnPlay = new Button();
btnPlay.Location = new Point(form.ClientSize.Width / 2 - 50, 70);
btnPlay.Size = new Size(100, 25);
btnPlay.Text = "Play";
tbFreq = new TrackBar();
tbFreq.Location = new Point(10, 10);
tbFreq.Size = new Size(form.ClientSize.Width - 20, 30);
tbFreq.Minimum = 250;
tbFreq.Maximum = 3000;
form.Controls.Add(tbFreq);
form.Controls.Add(btnPlay);
}
public static void WireUpButtonEvent()
{
btnPlay.Click += (sndr, args) =>
{
if (!playing)
{
MemoryStream stream = Play(player, tbFreq.Value);
player.Stream = stream;
player.PlayLooping();
stream.Close();
btnPlay.Text = "Stop";
playing = true;
}
else
{
player.Stop();
btnPlay.Text = "Play";
playing = false;
}
};
}
public static void WireUpTrackbarEvent()
{
tbFreq.ValueChanged += (sndr, args) =>
{
if (playing)
{
player.Stop();
MemoryStream stream = Play(player, tbFreq.Value);
player.Stream = stream;
player.PlayLooping();
stream.Close();
}
};
}
// Original code from http://stackoverflow.com/questions/12611982/generate-audio-tone-to-sound-card-in-c-or-c-sharp
public static MemoryStream Play(SoundPlayer player, int frequency, int msDuration = 1000)
{
var soundStream = new MemoryStream();
BinaryWriter writer = new BinaryWriter(soundStream);
int samplesPerSecond = 44100;
int samples = (int)((decimal)samplesPerSecond * msDuration / 1000);
WriteWavHeader(writer, msDuration, samplesPerSecond);
GenerateWaveform(writer, frequency, samples, samplesPerSecond);
soundStream.Seek(0, SeekOrigin.Begin);
return soundStream;
}
private static void WriteWavHeader(BinaryWriter writer, int msDuration, int samplesPerSecond)
{
int formatChunkSize = 16;
int headerSize = 8;
short formatType = 1;
short tracks = 1;
short bitsPerSample = 16;
short frameSize = (short)(tracks * ((bitsPerSample + 7) / 8));
int bytesPerSecond = samplesPerSecond * frameSize;
int waveSize = 4;
int samples = (int)((decimal)samplesPerSecond * msDuration / 1000);
int dataChunkSize = samples * frameSize;
int fileSize = waveSize + headerSize + formatChunkSize + headerSize + dataChunkSize;
writer.Write(0x46464952); // = encoding.GetBytes("RIFF")
writer.Write(fileSize);
writer.Write(0x45564157); // = encoding.GetBytes("WAVE")
writer.Write(0x20746D66); // = encoding.GetBytes("fmt ")
writer.Write(formatChunkSize);
writer.Write(formatType);
writer.Write(tracks);
writer.Write(samplesPerSecond);
writer.Write(bytesPerSecond);
writer.Write(frameSize);
writer.Write(bitsPerSample);
writer.Write(0x61746164); // = encoding.GetBytes("data")
writer.Write(dataChunkSize);
}
private static void GenerateWaveform(BinaryWriter writer, int frequency, int samples, int samplesPerSecond, int volume = 16383)
{
const double TAU = 2 * Math.PI;
double theta = frequency * TAU / (double)samplesPerSecond;
// 'volume' is UInt16 with range 0 thru Uint16.MaxValue ( = 65 535)
// we need 'amp' to have the range of 0 thru Int16.MaxValue ( = 32 767)
double amp = volume >> 2; // so we simply set amp = volume / 2
for (int step = 0; step < samples; step++)
{
short s = (short)(amp * Math.Sin(theta * (double)step));
writer.Write(s);
}
}
}
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment