STREAMPROC callback

User stream writing callback function.

DWORD CALLBACK StreamProc(
    HSTREAM handle,
    void *buffer,
    DWORD length,
    void *user
);

Parameters

handleThe stream that needs writing.
bufferPointer to the buffer to write the sample data in. The data should be as follows: 8-bit samples are unsigned, 16-bit samples are signed, 32-bit floating-point samples range from -1 to +1.
lengthThe maximum number of bytes to write.
userThe user instance data given when BASS_StreamCreate was called.

Return value

The number of bytes written by the function, optionally using the BASS_STREAMPROC_END flag to signify that the end of the stream is reached.

Remarks

A stream writing function should be as quick as possible because other playing streams (and MOD musics) cannot be updated until it has finished (unless multiple update threads are enabled via the BASS_CONFIG_UPDATETHREADS option). It is better to return less data quickly, rather than spending a long time delivering exactly the amount requested.

Although a STREAMPROC may return less data than BASS requests, be careful not to do so by too much, too often. If the buffer gets exhausted, BASS will automatically stall playback of the stream, until more data is provided. BASS_ChannelGetData (BASS_DATA_AVAILABLE) can be used to check the buffer level, and BASS_ChannelIsActive can be used to check if playback has stalled. A BASS_SYNC_STALL sync can also be set via BASS_ChannelSetSync, to be triggered upon playback stalling or resuming. If you do return less than the requested amount of data, the number of bytes should still equate to a whole number of samples.

The BASS_ATTRIB_GRANULE attribute can be used to control the granularity of the amount of data requested.

Some functions can cause problems if called from within a stream (or DSP) function. Do not call BASS_Stop or BASS_Free from within a stream callback, and do not call BASS_ChannelStop or BASS_ChannelFree or BASS_StreamFree with the same handle as received by the callback.

When streaming multi-channel sample data, the channel order of each sample is as follows.

3 channelsfront left, front right, center.
4 channelsfront left, front right, rear left, rear right.
5 channelsfront left, front right, center, rear left, rear right.
6 channels (5.1)front left, front right, center, LFE, rear left, rear right.
7 channels (6.1)front left, front right, center, LFE, rear center, side left, side right.
8 channels (7.1)front left, front right, center, LFE, rear left, rear right, side left, side right.

Example

A callback function to stream a file, in 44100 Hz stereo 16-bit.
FILE *file;
...
// the stream writing callback
DWORD CALLBACK MyStreamProc(HSTREAM handle, void *buffer, DWORD length, void *user)
{
    DWORD c = fread(buffer, 1, length, file); // read the file into the buffer
    if (feof(file)) c |= BASS_STREAMPROC_END; // end of the file/stream
    return c;
}
...
HSTREAM stream = BASS_StreamCreate(44100, 2, 0, MyStreamProc, 0); // create the stream

See also

BASS_StreamCreate, BASS_ATTRIB_GRANULE