I’m trying to merge WAV files and I found this code posted by Wayne Golding:
Sub JoinWaveFiles(InFile1 As FolderItem, InFile2 As FolderItem, OutFile As FolderItem)
Dim InData1 As MemoryBlock
Dim InData2 As MemoryBlock
Dim bsIn As BinaryStream
// Read the files into memory
bsIn = BinaryStream.Open(InFile1)
InData1 = bsIn.Read(bsIn.Length)
bsIn.Close
bsIn = BinaryStream.Open(InFile2)
InData2 = bsIn.Read(bsIn.Length)
bsIn.Close
// Create the joined Data
Dim OutData As New MemoryBlock(InData1.Size + InData2.Size - 44)
OutData = InData1 + InData2.MidB(44)
// Update the header
Dim chunksize As Integer = OutData.Size - 8
Dim subchunksize As Integer = OutData.Size - 44
OutData.Long(4) = chunksize
OutData.Long(40) = subchunksize
// Save the joined files to disk
Dim bsOut As BinaryStream
bsOut = BinaryStream.Create(OutFile, True)
bsOut.Write(OutData)
bsOut.Close
End Sub
It successfully joins the files but there is a clicking sound after each joined file. Does anyone know what might be causing the clicks?
Thanks!
So in sleuthing the code and learning more about WAV files than I had known before, my suspicion is that at the end of each of the files there’s some metadata that’s either RIFF INFO or ID3 tag data. Looking at the files in a hex editor confirms this (at least for the files I’m using).
So the code needs to be updated to exclude this metadata. Base upon the WAV specs it looks like starting at byte 40 and going over 4 bytes is the number of audio bytes within the file not including the header. I also ran into some endian issues so I had to correct for this as well. As I was already splicing together the bytes, I ended up just grabbing the header + audio data for file 1 and just the audio data for file 2, hence the output file code is slightly different as it’s a bit more streamlined (e.g. file 1 + file 2).
The files I tested against are:
- Alesis-S4-Plus-5ths-Lead-C5.wav
- Yamaha-V50-SoftLead-C4.wav
And here’s the updated code that gets rid of the clicks/static towards the end.
Updated Code
Dim InFile1 As FolderItem, InFile2 As FolderItem, OutFile As FolderItem
Dim InData1 As MemoryBlock
Dim InData2 As MemoryBlock
Dim bsIn As BinaryStream
Dim InData1AudioBytes As UInt32
Dim InData2AudioBytes As UInt32
InFile1 = SpecialFolder.Desktop.Child("1.wav")
InFile2 = SpecialFolder.Desktop.Child("2.wav")
OutFile = SpecialFolder.Desktop.Child("3.wav")
// Read the files into memory
// InFile1
bsIn = BinaryStream.Open(InFile1)
bsIn.LittleEndian = True
bsIn.BytePosition = 40
InData1AudioBytes = bsIn.ReadUInt32 // 4 Bytes for number of bytes in the audio data
bsIn.BytePosition = 0
InData1 = bsIn.Read(44 + InData1AudioBytes) // +44 for Header
bsIn.Close
// InFile2
bsIn = BinaryStream.Open(InFile2)
bsIn.LittleEndian = True
bsIn.BytePosition = 40
InData2AudioBytes = bsIn.ReadInt32 // 4 Bytes for number of bytes in the audio data
bsIn.BytePosition = 44
InData2 = bsIn.Read(InData2AudioBytes)
bsIn.Close
// Create the joined Data
Dim OutData As New MemoryBlock(InData1.Size + InData2.Size)
OutData = InData1 + InData2
// Update the header
Dim chunksize As Integer = OutData.Size - 8
Dim subchunksize As Integer = OutData.Size - 44
OutData.Long(4) = chunksize
OutData.Long(40) = subchunksize
// Save the joined files to disk
Dim bsOut As BinaryStream
bsOut = BinaryStream.Create(OutFile, True)
bsOut.Write(OutData)
bsOut.Close
4 Likes
Patrick, that’s awesome! The clicks are gone. Thank you so much!
1 Like