Upsample Audio¶
This article explains how to upsample an audio clip from 44.1 Khz to 48 KHz.
Source Audio¶
For an audio source we use the kahvi011_kennybeltrey-hydrate.mp3 file from the Internet Archive. The original audio format is MPEG Audio Layer 3, 44.1 KHz, Joint Stereo, 136 Kbps, Variable Bit Rate
Sample Code¶
This code takes an MP3 file with 44.1 KHz audio, and converts it to an MP3 file with 48 KHz audio using polyphase resampling method. The input and output file paths are hardcoded in the source code, no command line parsing is used.
The snippets in this section are from the simple_audio_upsample .NET sample.
Initialize AVBlocks¶
The first step in any AVBlocks application is to initialize the library. This must be done before using any other AVBlocks functionality. The Library.Initialize() method sets up the internal state and loads necessary codecs. Always remember to call Library.Shutdown() at the end of your program to properly clean up resources and release any allocated memory.
string inputPath = "kahvi011_kennybeltrey-hydrate.mp3";
string outputPath = "kahvi011_kennybeltrey-hydrate_48Khz.mp3";
Library.Initialize();
bool result = Upsample(inputPath, outputPath);
Library.Shutdown();
Configure Transcoder and Upsample¶
We probe the input file with a MediaInfo object, and create an input socket from it. The output socket is created by cloning the input socket, so it starts out with an identical configuration, and then we set the output file path on it. The transcoder is the core component that performs the actual upsampling - it takes the 44.1 KHz audio from the input and resamples it to 48 KHz using polyphase resampling for the best upsampling quality.
Probe Input and Create Sockets¶
First, we probe the input file and create the input socket. Then we clone it to create the output socket and set the output file path.
using (var mediaInfo = new MediaInfo())
{
mediaInfo.Inputs[0].File = inputPath;
if (!mediaInfo.Open())
{
PrintError("Open MediaInfo", mediaInfo.Error);
return false;
}
var inputSocket = MediaSocket.FromMediaInfo(mediaInfo);
// Clone the input socket to start with identical output configuration
var outputSocket = (MediaSocket)inputSocket.Clone();
outputSocket.File = outputPath;
// ...
}
Change Sampling Rate¶
Next, we get the output audio pin and change the sampling rate from 44.1 KHz to 48 KHz.
if (outputSocket.Pins.Count > 0)
{
var outAudioPin = outputSocket.Pins[0];
var outAudioStream = outAudioPin.StreamInfo as AudioStreamInfo;
if (outAudioStream != null)
{
outAudioStream.SampleRate = 48000;
}
}
Create Transcoder and Run¶
Finally, we create the transcoder, configure it with the input and output sockets, and run it.
using (var transcoder = new Transcoder())
{
transcoder.AllowDemoMode = true;
transcoder.Inputs.Add(inputSocket);
transcoder.Outputs.Add(outputSocket);
if (!transcoder.Open())
{
PrintError("Transcoder open", transcoder.Error);
return false;
}
if (!transcoder.Run())
{
PrintError("Transcoder run", transcoder.Error);
transcoder.Close();
return false;
}
transcoder.Close();
}
Complete Code¶
Here’s the complete working example that demonstrates audio upsampling using AVBlocks for .NET.
using System;
using System.IO;
using PrimoSoftware.AVBlocks;
namespace SimpleAudioUpsample
{
class Program
{
static int Main(string[] args)
{
// Hardcoded input and output file paths (no command line parsing)
// Paths are relative to the working directory from which the executable is run
string inputPath = "kahvi011_kennybeltrey-hydrate.mp3";
string outputPath = "kahvi011_kennybeltrey-hydrate_48Khz.mp3";
Library.Initialize();
bool result = Upsample(inputPath, outputPath);
Library.Shutdown();
return result ? (int)ExitCodes.Success : (int)ExitCodes.EncodingError;
}
static bool Upsample(string inputPath, string outputPath)
{
// Ensure output directory exists
string outputDir = Path.GetDirectoryName(outputPath);
if (!string.IsNullOrEmpty(outputDir) && !Directory.Exists(outputDir))
{
Directory.CreateDirectory(outputDir);
}
// Delete output file if it exists (transcoder will fail otherwise)
if (File.Exists(outputPath))
{
File.Delete(outputPath);
}
// Create MediaInfo to probe the input file
using (var mediaInfo = new MediaInfo())
{
mediaInfo.Inputs[0].File = inputPath;
if (!mediaInfo.Open())
{
PrintError("Open MediaInfo", mediaInfo.Error);
return false;
}
// Create input socket from probed media info
var inputSocket = MediaSocket.FromMediaInfo(mediaInfo);
// Clone the input socket to start with identical output configuration
var outputSocket = (MediaSocket)inputSocket.Clone();
outputSocket.File = outputPath;
// Get the output audio pin and set sample rate to 48 KHz
if (outputSocket.Pins.Count > 0)
{
var outAudioPin = outputSocket.Pins[0];
var outAudioStream = outAudioPin.StreamInfo as AudioStreamInfo;
if (outAudioStream != null)
{
outAudioStream.SampleRate = 48000;
}
}
// Create Transcoder and configure it
using (var transcoder = new Transcoder())
{
transcoder.AllowDemoMode = true;
transcoder.Inputs.Add(inputSocket);
transcoder.Outputs.Add(outputSocket);
if (!transcoder.Open())
{
PrintError("Transcoder open", transcoder.Error);
return false;
}
if (!transcoder.Run())
{
PrintError("Transcoder run", transcoder.Error);
transcoder.Close();
return false;
}
transcoder.Close();
}
}
return true;
}
static void PrintError(string action, ErrorInfo e)
{
if (action != null)
{
Console.Write("{0}: ", action);
}
if (ErrorFacility.Success == e.Facility)
{
Console.WriteLine("Success");
return;
}
else
{
Console.WriteLine("{0}, facility:{1} code:{2} hint:{3}", e.Message ?? "", e.Facility, e.Code, e.Hint ?? "");
}
}
enum ExitCodes : int
{
Success = 0,
OptionsError = 1,
EncodingError = 2,
}
}
}
How to Run¶
This sample uses hardcoded file paths — no command line arguments.
Prerequisites¶
Download the sample audio file from the Internet Archive:
curl -L -o kahvi011_kennybeltrey-hydrate.mp3 \
https://archive.org/download/kahvi011/kahvi011_kennybeltrey-hydrate.mp3
Running¶
Run the sample from the sample directory (the input/output file paths are relative to the working directory):
../../bin/net10.0/simple_audio_upsample
The upsampled output file kahvi011_kennybeltrey-hydrate_48Khz.mp3 will be created in the current directory.
Notes¶
The input file
kahvi011_kennybeltrey-hydrate.mp3and output filekahvi011_kennybeltrey-hydrate_48Khz.mp3paths are hardcoded inProgram.cs. They are relative to the working directory.If the transcoder fails, the output file may already exist. Delete it and try again.
The output audio stream is resampled from 44.1 KHz to 48 KHz using AVBlocks’ polyphase resampling method.