Skip to content

Commit dad2fe8

Browse files
committed
waveform rendering to PNG documentation
1 parent 1f0fed4 commit dad2fe8

File tree

3 files changed

+82
-2
lines changed

3 files changed

+82
-2
lines changed

Docs/WaveFormRendering.md

+79
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,79 @@
1+
# Render an Audio Wave Form to PNG
2+
3+
NAudio does not include any visualization code in the core library, but it does provid access to the raw audio samples which you need to render wave-forms.
4+
5+
NAudio does however provide a sample project at GitHub: [NAudio.WaveFormRenderer](https://github.com/naudio/NAudio.WaveFormRenderer) which makes use of `NAudio` and `System.Drawing` to render waveforms in a variety of styles.
6+
7+
![Orange Blocks](https://cloud.githubusercontent.com/assets/147668/18606778/5a9516ac-7cb1-11e6-8660-a0a80d72fe26.png)
8+
9+
## WaveFormRendererLib
10+
11+
The `WaveFormRendererLib` project contains a customizable waveform rendering algorithm, allowing you to
12+
13+
The waveform rendering algorithm is customizable:
14+
15+
- Supports several peak calculation strategies (max, average, sampled, RMS, decibels)
16+
- Supports different colors or gradients for the top and bottom half
17+
- Supports different sizes for top and bottom half
18+
- Overall image size and background can be customized
19+
- Transparent backgrounds
20+
- Support for SoundCloud style bars
21+
- Several built-in rendering styles
22+
23+
## WaveFormRenderer
24+
25+
The `WaveFormRenderer` class allows easy rendering of files. We need to create some configuration options first.
26+
27+
The peak provider decides how peaks are calculated. There are four built in options you can choose from. `MaxPeakProvider` simply picks out the maximum sample value in the timeblock that each bar represents. `RmsPeakProvider` calculates the root mean square of each sample and returns the maximum value found in a specified blcok. The `SamplingPeakProvider` simply samples the samples, and you pass in a sample interval.Finally the `AveragePeakProvider` averages the sample values and takes a scale parameter to multiply the average by as it tends to produce lower values.
28+
29+
```c#
30+
var maxPeakProvider = new MaxPeakProvider();
31+
var rmsPeakProvider = new RmsPeakProvider(blockSize); // e.g. 200
32+
var samplingPeakProvider = new SamplingPeakProvider(sampleInterval); // e.g. 200
33+
var averagePeakProvider = new AveragePeakProvider(scaleFactor); // e.g. 4
34+
```
35+
36+
Next we need to provide the rendering settings. This is an instance of `WaveFormRendererSettings` which specifies:
37+
38+
- **Width** - the width of the rendered image in pixels
39+
- **TopHeight** - height of the top half of the waveform in pixels
40+
- **BottomHeight** - height of the bottom half of the waveform in pixels. Normally set to the same as `TopHeight` but can be 0 or smaller for asymmetric waveforms
41+
- **PixelsPerPeak** - allows for wider bars to represent each peak. Usually set to 1.
42+
- **SpacerPixels** - allows blank spaces to be inserted between vertical bars. Usually 0 unless when wide bars are used.
43+
- **TopPeakPen** - Pen to draw the top bars with
44+
- **TopSpacerPen** - Pen to draw the top spacer bars with
45+
- **BottomPeakPen** - Pen to draw the bottom bars with
46+
- **BottomSpacerPen** - Pen to draw the bottom spacer bars with
47+
- **DecibelScale** - if true, convert values to decibels for a logarithmic waveform
48+
- **BackgroundColor** - background color (used if no `BackgroundImage` is specified)
49+
- **BackgroundImage** - background image (alternative to solid color)
50+
51+
To simplify setting up an instance of `WaveFormRendererSettings` several derived types are supplied including
52+
`StandardWaveFormRendererSettings`, `SoundCloudOriginalSettings` and `SoundCloudBlockWaveFormSettings`. The latter two mimic rendering styles that have been used by SoundCloud in the past.
53+
54+
```c#
55+
var myRendererSettings = new StandardWaveFormRendererSettings();
56+
myRendererSettings.Width = 640;
57+
myRendererSettings.TopHeight = 32;
58+
myRendererSettings.BottomHeight = 32;
59+
```
60+
61+
Now we just need to create our `WaveFormRenderer` and give it a path to the file we want to render, and pass in the peak provider we've chosen and the renderer settings:
62+
63+
```C#
64+
var renderer = new WaveFormRenderer();
65+
var audioFilePath = "myfile.mp3";
66+
var image = renderer.Render(audioFilePath, myPeakProvider, myRendererSettings);
67+
```
68+
69+
With that image we could render it to a WinForms picturebox:
70+
```c#
71+
pictureBox1.Image = image;
72+
```
73+
74+
Or we could save it to a PNG file which you'd want to do if you were rendering on a web server for example:
75+
```c#
76+
image.Save("myfile.png", ImageFormat.Png);
77+
```
78+
79+

NAudio.sln

+2-1
Original file line numberDiff line numberDiff line change
@@ -1,7 +1,7 @@
11

22
Microsoft Visual Studio Solution File, Format Version 12.00
33
# Visual Studio 15
4-
VisualStudioVersion = 15.0.27004.2006
4+
VisualStudioVersion = 15.0.27004.2009
55
MinimumVisualStudioVersion = 10.0.40219.1
66
Project("{FAE04EC0-301F-11D3-BF4B-00C04F79EFBC}") = "NAudio", "NAudio\NAudio.csproj", "{DA4F02E3-0B5E-42CD-B8D9-5583FA51D66E}"
77
EndProject
@@ -54,6 +54,7 @@ Project("{2150E333-8FDC-42A3-9474-1A3956D46DE8}") = "Docs", "Docs", "{BA7F6DBB-9
5454
Docs\RecordWavFileWinFormsWaveIn.md = Docs\RecordWavFileWinFormsWaveIn.md
5555
Docs\WasapiLoopbackCapture.md = Docs\WasapiLoopbackCapture.md
5656
Docs\WasapiOut.md = Docs\WasapiOut.md
57+
Docs\WaveFormRendering.md = Docs\WaveFormRendering.md
5758
Docs\WaveProviders.md = Docs\WaveProviders.md
5859
EndProjectSection
5960
EndProject

README.md

+1-1
Original file line numberDiff line numberDiff line change
@@ -116,7 +116,7 @@ NAudio comes with several demo applications which are the quickest way to see ho
116116

117117
### Visualization
118118

119-
- [WaveForm Rendering to PNG](http://markheath.net/post/naudio-png-waveform-rendering)
119+
- [WaveForm Rendering to PNG](Docs/WaveFormRendering.md)
120120

121121
### MIDI
122122

0 commit comments

Comments
 (0)