How to merge / concatenate mp3s with PHP
One of the new features of my anti-spam plugin is the ability to create auto-generated mp3 files. The plugin concatenates individual mp3 files representing the sound of each letter in the alphabet, in order to build a word.
Of course, I have no idea how to code something that merges mp3 files, so I had to do some searching and eventually found this site with some working code: http://www.sourcerally.net/Scripts/20-PHP-MP3-Class.
Here is my modified version, with some simplified functionality (I removed the code that added ID3 tags) and an added feature that I modified from FPDF (a script that creates PDFs in PHP) in order to output (to the browser) the merged mp3 file, prompting users to open or save it. This code is compatible with both PHP 4 and PHP 5.
<?php
// This is the class to generate mp3 files based on the anti-spam words
// Based on the PHP mp3 class at http://www.sourcerally.net/Scripts/20-PHP-MP3-Class
// Output code based on the FPDF class at http://www.fpdf.org
class mp3
{
var $str;
var $time;
var $frames;
// Create a new mp3
function mp3($path="")
{
if($path!="")
{
$this->str = file_get_contents($path);
}
}
// Put an mp3 behind the first mp3
function mergeBehind($mp3)
{
$this->str .= $mp3->str;
}
// Calculate where's the end of the sound file
function getIdvEnd()
{
$strlen = strlen($this->str);
$str = substr($this->str,($strlen-128));
$str1 = substr($str,0,3);
if(strtolower($str1) == strtolower('TAG'))
{
return $str;
}
else
{
return false;
}
}
// Calculate where's the beginning of the sound file
function getStart()
{
$strlen = strlen($this->str);
for($i=0;$i<$strlen;$i++)
{
$v = substr($this->str,$i,1);
$value = ord($v);
if($value == 255)
{
return $i;
}
}
}
// Remove the ID3 tags
function striptags()
{
//Remove start stuff...
$newStr = '';
$s = $start = $this->getStart();
if($s===false)
{
return false;
}
else
{
$this->str = substr($this->str,$start);
}
//Remove end tag stuff
$end = $this->getIdvEnd();
if($end!==false)
{
$this->str = substr($this->str,0,(strlen($this->str)-129));
}
}
// Display an error
function error($msg)
{
//Fatal error
die('<strong>audio file error: </strong>'.$msg);
}
// Send the new mp3 to the browser
function output($path)
{
//Output mp3
//Send to standard output
if(ob_get_contents())
$this->error('Some data has already been output, can\'t send mp3 file');
if(php_sapi_name()!='cli')
{
//We send to a browser
header('Content-Type: audio/mpeg3');
if(headers_sent())
$this->error('Some data has already been output to browser, can\'t send mp3 file');
header('Content-Length: '.strlen($this->str));
header('Content-Disposition: attachment; filename="'.$path.'"');
}
echo $this->str;
return '';
}
}
?>
Here’s how I used the class to generate an mp3 file from individual files (in a “sounds” folder) representing each letter. You can, of course, use the above code to concatenate mp3 files for any purpose.
// Specify the word
$petersword = "testword";
$word_count = strlen($petersword);
// Set up the first file
if ($word_count > 0) {
$mp3 = new mp3($cas_fontpath . 'sounds/' . substr($petersword, 0, 1) . '.mp3');
$mp3->striptags();
}
// Generate the mp3 file from each letter in the word
for ($i = 1; $i < $word_count; ++$i) {
$cas_character = $cas_fontpath . 'sounds/' . substr($petersword, $i, 1);
$cas_mp3equivalent = new mp3($cas_character . '.mp3');
$mp3->mergeBehind($cas_mp3equivalent);
$mp3->striptags();
}
// Spit out the audio file!
$mp3->output('word.mp3');
Note: if you need some support using any of the code, I suggest that you visit the original source of the mp3 concatenation code.

keung.biz. Hire my web consulting services at
Follow us on Twitter



January 15th, 2008 at 11:42 am

Priyankoo Sarmah says:
Thanks a lot!! So useful!!
March 1st, 2008 at 12:10 pm

Alx says:
do it is possible to insert a pause into file merged?
March 1st, 2008 at 1:19 pm

Peter says:
Yes, you can insert a pause — to do so you simply have to record a blank sound file as the pause.
March 2nd, 2008 at 8:19 am

Alx says:
This is my implementation:
http://interno.netsons.org/modules.php?name=Dtmf
http://interno.netsons.org/modules.php?name=Banche
http://interno.netsons.org/modules.php?name=CodFis
Ty
June 30th, 2008 at 7:59 pm

Dada says:
I was looking for that sort of script since severals months, you’re my hero, thanks alot.
July 1st, 2009 at 11:30 am

Thierry says:
Thanks for sharing. It worked on the first try … what I though would take hours, take me 30mn …
July 8th, 2009 at 8:57 pm

Vaz says:
Excellent…I thought we need some extra things to work mp3 with php…great tutorial
June 1st, 2010 at 1:19 pm

Mukoo says:
Thanks! it works perfectly. But how about layering/mixdown 2 mp3′s, not simply appending one after the other. What if I want them to blend together? Do you think it can be done?
Reply from Peter: It can certainly be done with desktop programs, but I’ve never looked into a command-line solution. If you find something, please post your findings.
August 3rd, 2010 at 1:59 am

Natali says:
Very helpfull!!! Many thanks!!!
October 5th, 2010 at 2:19 am

Sarunas says:
When merging mp3s with different bitrates the higher bitrate mp3 plays in slow motion. Any solutions to this?
Reply from Peter: Not sure, but I welcome other people’s solutions.
December 19th, 2010 at 8:48 am

Michel says:
This script is exactly what I was looking for but… is there a way to have the sound played by a flash script like hbs_mp3_player.swf directly in the web page?
When I use your script I’m asked to download the merged mp3 file or play it with VLC or WMP.
Reply from Peter: I’m pretty sure you could feed the generated file to a player, since it shouldn’t be any different than any other mp3 player. If it’s a file being generated on the fly, you probably have to save it to the server and stream it from there.
November 9th, 2011 at 10:37 am

John C says:
Dear all,
I am a beginner with php. I would like to adapt this script to merge 2 mp3 files (file1.mp3 and file2.mp3 into file-merged.mp3).
It should be very simple compared to this script.
Thank you very much for your kind replies.
JC