Hi, Can anyone tell me how to combine 2 or more wav files on runtime and play them? I need VB6 code. And at same time I wud like to know how to add duration for a wav sound. For example: C# note.wav - for 4 secs
: Hi, : Can anyone tell me how to combine 2 or more wav files on runtime and play them? I need VB6 code. : And at same time I wud like to know how to add duration for a wav sound. : For example: : C# note.wav - for 4 secs : : I'm having the same problem with combining wave data during playback, However,for the second prob,This *might* work. Make sure that the wave data in c#note.wav has a similar endind point, to the starting in the wave data,that is, it begins and ends with the same sample value(to pevent an audible glitch) and send the data over and over again, until the sound is no longer needed. To do this, I would not store more than one wavelength in the file to start, and cut the down slope off/ rewrite it to look like the upslope going down.(to get a simetrical wave that begins and ends with the same sample value) also, no silence at the begining or end of the data can be present. then, i would copy the single wave to memory, and create a timer to send the single wavelength to the sound card continually, every time the sample is about to run out. All you have to do to stop the wave is stop the timer. This may take too much process time, so i would(if needed)double my wavedata and and timer length, until i got to a suitable cpu cost. However, each time you double the wave data, you increase needed storage for the data, and you lower the presision of the stop point. Keep in mind, that I havn't done this, and I don't know if it will work, but it's what i would try first if I was to code this. Also, You may want to rethink your lingo, VB may not give you the level of controll/speed you need t do what I think you want to do. You should either consider coding in C,C++, or just use General Midi to sustain this C# note for invariable amouns of time.If i was you, I would Just use general midi
Shameless plug: I have a site (www.Cafe441.com) that I am putting together to help answer some of these types of audio programming questions.
Question 1: I notice that this has been brought up a few times on this board. Basically what you want to do is mix the audio data that you are sending to the Windows sound handler at run time. In order to do this you can basically add the two bitstreams together (the raw PCM part after the .wav file header, this is usually offeset at 44 bytes into the wav file). The only problem is that the values cannot exceed the maximum values when you do this or you will get distorion. 16 bit values must be capped at 32767 and -32767 and 8 bit samples are bound at 0 and 128 (signed and unsigned depending on the bit size? It's true!). So in order to do this you must either: a) Clip all samples that are outside the allowable boundries (sucks). b) Turn down the amplitude on each sample before mixing (better).
To clip just do something like Value = Min(Max(A + B,-32767),32767). To turn down the amplitude before mixing just do:
For each sample value do NewValue = SampleValue * 0.5
That should do the trick (I took the liberties of pseudo code).
Question 2:
Basically what you are getting at is the question of time shifting. This is a huge topic and beyond the scope of what can be discussed here. HOWEVER, if you just want to play one constant tone then all you have to do is create a waveform generation function and keep sending data to the player from the function for the duration of the tone. Attack and sustain can be modelled by altering the amplitudes at the respective times.
I believe that what you are getting at though is actually taking a wav file and stretching the time it plays which is time shifting and very complex.
: : Hi, : : Can anyone tell me how to combine 2 or more wav files on runtime and play them? I need VB6 code. : : And at same time I wud like to know how to add duration for a wav sound. : : For example: : : C# note.wav - for 4 secs : : : : : I'm having the same problem with combining wave data during playback, However,for the second prob,This *might* work. Make sure that the wave data in c#note.wav has a similar endind point, to the starting in the wave data,that is, it begins and ends with the same sample value(to pevent an audible glitch) and send the data over and over again, until the sound is no longer needed. To do this, I would not store more than one wavelength in the file to start, and cut the down slope off/ rewrite it to look like the upslope going down.(to get a simetrical wave that begins and ends with the same sample value) also, no silence at the begining or end of the data can be present. then, i would copy the single wave to memory, and create a timer to send the single wavelength to the sound card continually, every time the sample is about to run out. All you have to do to stop the wave is stop the timer. This may take too much process time, so i would(if needed)double my wavedata and and timer length, until i got to a suitable cpu cost. However, each time you double the wave data, you increase needed storage for the data, and you lower the presision of the stop point. Keep in mind, that I havn't done this, and I don't know if it will work, but it's what i would try first if I was to code this. Also, You may want to rethink your lingo, VB may not give you the level of controll/speed you need t do what I think you want to do. You should either consider coding in C,C++, or just use General Midi to sustain this C# note for invariable amouns of time.If i was you, I would Just use general midi :
[b][red]This message was edited by shadow451 at 2003-11-30 6:29:45[/red][/b][hr] [b][red]This message was edited by shadow451 at 2003-11-30 5:3:37[/red][/b][hr] [b][red]This message was edited by shadow451 at 2003-11-30 4:35:19[/red][/b][hr] [b][red]This message was edited by shadow451 at 2003-11-30 4:24:38[/red][/b][hr] You can take the PCM data from your source samples and interpolate the values of the mixed sample by writing the greater amplitude value of your sources to your mixed sample.
In C++ something like this:
//the sample_size variable depends on //the resolution(unsigned 8 bit, signed 16 bit or 32 bit floating point) //and sample rate and should be uniform or of the same type //for all of your buffers
//set up a loop counter register short int loop = 0;
//set up your buffers float Sample1[sample_size]; float Sample2[sample_size]; float MixedSample[sample_size];
//start looping and compare sources for greater value //and write the higher value to your output buffer while(loop < sample_size) { if(Sample1[loop] > Sample2[loop])MixedSample[loop] = Sample1[loop]; else MixedSample[loop] = Sample2[loop]; loop++; }
Using this method rather than summing the values keeps your values within the correct range and the levels of your sources are the same in your mixed down sample. Simply summing the values means you have to make sure they stay within the sample types range or the result is clipping. Also summing the values allows the actual levels of your input sources to be modulated by each other, not usually a desirable effect.
This is simplified and straightforward code In the real world there's a little more to it but you get the idea.
NOTES
The example above is staright C code. I've written a couple of classes in C++ to handle this kind of stuff.
I would recommend allocating the buffers from the heap and not the stack.
This method is for non playback mixing. If you use this for real time mixing then you should run this process in a seperate normal priority thread and process 250 millisecond blocks at a time rather than each sample. Sample rates of 22050 or higher recommended.
If your just wanting to playback a mixed sound then it's much easier to just let the sound hardware or DirectSounds HEL(hardware emulation layer) handle it.
Comments
: Can anyone tell me how to combine 2 or more wav files on runtime and play them? I need VB6 code.
: And at same time I wud like to know how to add duration for a wav sound.
: For example:
: C# note.wav - for 4 secs
:
:
I'm having the same problem with combining wave data during playback, However,for the second prob,This *might* work. Make sure that the wave data in c#note.wav has a similar endind point, to the starting in the wave data,that is, it begins and ends with the same sample value(to pevent an audible glitch) and send the data over and over again, until the sound is no longer needed. To do this, I would not store more than one wavelength in the file to start, and cut the down slope off/ rewrite it to look like the upslope going down.(to get a simetrical wave that begins and ends with the same sample value) also, no silence at the begining or end of the data can be present. then, i would copy the single wave to memory, and create a timer to send the single wavelength to the sound card continually, every time the sample is about to run out. All you have to do to stop the wave is stop the timer. This may take too much process time, so i would(if needed)double my wavedata and and timer length, until i got to a suitable cpu cost. However, each time you double the wave data, you increase needed storage for the data, and you lower the presision of the stop point. Keep in mind, that I havn't done this, and I don't know if it will work, but it's what i would try first if I was to code this. Also, You may want to rethink your lingo, VB may not give you the level of controll/speed you need t do what I think you want to do. You should either consider coding in C,C++, or just use General Midi to sustain this C# note for invariable amouns of time.If i was you, I would Just use general midi
deleted
deleted
Shameless plug:
I have a site (www.Cafe441.com) that I am putting together to help answer some of these types of audio programming questions.
Question 1:
I notice that this has been brought up a few times on this board. Basically what you want to do is mix the audio data that you are sending to the Windows sound handler at run time. In order to do this you can basically add the two bitstreams together (the raw PCM part after the .wav file header, this is usually offeset at 44 bytes into the wav file). The only problem is that the values cannot exceed the maximum values when you do this or you will get distorion. 16 bit values must be capped at 32767 and -32767 and 8 bit samples are bound at 0 and 128 (signed and unsigned depending on the bit size? It's true!). So in order to do this you must either:
a) Clip all samples that are outside the allowable boundries (sucks).
b) Turn down the amplitude on each sample before mixing (better).
To clip just do something like Value = Min(Max(A + B,-32767),32767).
To turn down the amplitude before mixing just do:
For each sample value do
NewValue = SampleValue * 0.5
That should do the trick (I took the liberties of pseudo code).
Question 2:
Basically what you are getting at is the question of time shifting. This is a huge topic and beyond the scope of what can be discussed here. HOWEVER, if you just want to play one constant tone then all you have to do is create a waveform generation function and keep sending data to the player from the function for the duration of the tone. Attack and sustain can be modelled by altering the amplitudes at the respective times.
I believe that what you are getting at though is actually taking a wav file and stretching the time it plays which is time shifting and very complex.
: : Hi,
: : Can anyone tell me how to combine 2 or more wav files on runtime and play them? I need VB6 code.
: : And at same time I wud like to know how to add duration for a wav sound.
: : For example:
: : C# note.wav - for 4 secs
: :
: :
: I'm having the same problem with combining wave data during playback, However,for the second prob,This *might* work. Make sure that the wave data in c#note.wav has a similar endind point, to the starting in the wave data,that is, it begins and ends with the same sample value(to pevent an audible glitch) and send the data over and over again, until the sound is no longer needed. To do this, I would not store more than one wavelength in the file to start, and cut the down slope off/ rewrite it to look like the upslope going down.(to get a simetrical wave that begins and ends with the same sample value) also, no silence at the begining or end of the data can be present. then, i would copy the single wave to memory, and create a timer to send the single wavelength to the sound card continually, every time the sample is about to run out. All you have to do to stop the wave is stop the timer. This may take too much process time, so i would(if needed)double my wavedata and and timer length, until i got to a suitable cpu cost. However, each time you double the wave data, you increase needed storage for the data, and you lower the presision of the stop point. Keep in mind, that I havn't done this, and I don't know if it will work, but it's what i would try first if I was to code this. Also, You may want to rethink your lingo, VB may not give you the level of controll/speed you need t do what I think you want to do. You should either consider coding in C,C++, or just use General Midi to sustain this C# note for invariable amouns of time.If i was you, I would Just use general midi
:
[b][red]This message was edited by shadow451 at 2003-11-30 5:3:37[/red][/b][hr]
[b][red]This message was edited by shadow451 at 2003-11-30 4:35:19[/red][/b][hr]
[b][red]This message was edited by shadow451 at 2003-11-30 4:24:38[/red][/b][hr]
You can take the PCM data from your source samples and interpolate the values of the mixed sample by writing the greater amplitude value of your sources to your mixed sample.
In C++ something like this:
//the sample_size variable depends on
//the resolution(unsigned 8 bit, signed 16 bit or 32 bit floating point)
//and sample rate and should be uniform or of the same type
//for all of your buffers
//set up a loop counter
register short int loop = 0;
//set up your buffers
float Sample1[sample_size];
float Sample2[sample_size];
float MixedSample[sample_size];
//start looping and compare sources for greater value
//and write the higher value to your output buffer
while(loop < sample_size)
{
if(Sample1[loop] > Sample2[loop])MixedSample[loop] = Sample1[loop];
else MixedSample[loop] = Sample2[loop];
loop++;
}
Using this method rather than summing the values
keeps your values within the correct range and
the levels of your sources are the same in your mixed down
sample.
Simply summing the values means you have to make sure
they stay within the sample types range or the result
is clipping.
Also summing the values allows the actual levels of
your input sources to be modulated by each other,
not usually a desirable effect.
This is simplified and straightforward code
In the real world there's a little more to it
but you get the idea.
NOTES
The example above is staright C code.
I've written a couple of classes in C++ to handle this kind
of stuff.
I would recommend allocating the buffers from
the heap and not the stack.
This method is for non playback mixing.
If you use this for real time mixing then
you should run this process in a seperate
normal priority thread and process 250 millisecond
blocks at a time rather than each sample.
Sample rates of 22050 or higher recommended.
If your just wanting to playback a mixed sound then it's
much easier to just let the sound hardware or
DirectSounds HEL(hardware emulation layer) handle it.