mirror of
https://github.com/ZDoom/fluidsynth.git
synced 2024-12-01 00:21:14 +00:00
Added correct spelling of FLUID_SEQ_PITCHWHEELSENS with backwards compatible misspelled symbol.
Added FLUID_OK and FLUID_FAILED to public API (misc.h). Renamed parameter of new_fluid_sequencer2() to use_system_timer. Renamed fludi_sequencer_get_useSystemTimer() to fluid_sequencer_get_use_system_timer(). Added missing FLUIDSYNTH_API to fluid_sequencer_add_midi_event_to_buffer(). Declared many local functions as static. Changed settings in doc/Doxyfile to only extract public documentation. Tons and tons of documentation updates on public API.
This commit is contained in:
parent
76777760ce
commit
420ba8198f
36 changed files with 1188 additions and 966 deletions
|
@ -50,7 +50,7 @@ TYPEDEF_HIDES_STRUCT = NO
|
|||
#---------------------------------------------------------------------------
|
||||
# Build related configuration options
|
||||
#---------------------------------------------------------------------------
|
||||
EXTRACT_ALL = YES
|
||||
EXTRACT_ALL = NO
|
||||
EXTRACT_PRIVATE = NO
|
||||
EXTRACT_STATIC = YES
|
||||
EXTRACT_LOCAL_CLASSES = NO
|
||||
|
@ -95,43 +95,11 @@ WARN_LOGFILE =
|
|||
#---------------------------------------------------------------------------
|
||||
INPUT = fluidsynth-v11-devdoc.txt \
|
||||
../include \
|
||||
../include/fluidsynth \
|
||||
../src
|
||||
INPUT_ENCODING = UTF-8
|
||||
FILE_PATTERNS = fluidsynth.h \
|
||||
audio.h \
|
||||
event.h \
|
||||
gen.h \
|
||||
log.h \
|
||||
midi.h \
|
||||
misc.h \
|
||||
mod.h \
|
||||
ramsfont.h \
|
||||
seq.h \
|
||||
seqbind.h \
|
||||
settings.h \
|
||||
sfont.h \
|
||||
shell.h \
|
||||
synth.h \
|
||||
types.h \
|
||||
version.h \
|
||||
voice.h \
|
||||
fluid_adriver.c \
|
||||
fluid_cmd.c \
|
||||
fluid_event.c \
|
||||
fluid_filerenderer.c \
|
||||
fluid_gen.c \
|
||||
fluid_sys.c \
|
||||
fluid_mdriver.c \
|
||||
fluid_midi.* \
|
||||
fluid_midi_router.* \
|
||||
fluid_mod.c \
|
||||
fluid_ramsfont.c \
|
||||
fluid_seq.c \
|
||||
fluid_seqbind.c \
|
||||
fluid_settings.c \
|
||||
fluid_synth.c \
|
||||
fluid_voice.c
|
||||
RECURSIVE = YES
|
||||
FILE_PATTERNS = *.[ch]
|
||||
RECURSIVE = NO
|
||||
EXCLUDE =
|
||||
EXCLUDE_SYMLINKS = NO
|
||||
EXCLUDE_PATTERNS =
|
||||
|
@ -146,7 +114,7 @@ FILTER_SOURCE_FILES = NO
|
|||
#---------------------------------------------------------------------------
|
||||
# configuration options related to source browsing
|
||||
#---------------------------------------------------------------------------
|
||||
SOURCE_BROWSER = YES
|
||||
SOURCE_BROWSER = NO
|
||||
INLINE_SOURCES = NO
|
||||
STRIP_CODE_COMMENTS = YES
|
||||
REFERENCED_BY_RELATION = NO
|
||||
|
|
|
@ -37,7 +37,6 @@ extern "C" {
|
|||
* audio driver (although it is not as efficient).
|
||||
*
|
||||
* @sa @ref CreatingAudioDriver
|
||||
* @{
|
||||
*/
|
||||
|
||||
/**
|
||||
|
@ -47,7 +46,7 @@ extern "C" {
|
|||
* @param data The user data parameter as passed to new_fluid_audio_driver2().
|
||||
* @param len Length of the audio in frames.
|
||||
* @param nin Count of buffers in 'in'
|
||||
* @param in FIXME - Not used currently?
|
||||
* @param in Not used currently
|
||||
* @param nout Count of arrays in 'out' (i.e., channel count)
|
||||
* @param out Output buffers, one for each channel
|
||||
* @return Should return 0 on success, non-zero if an error occured.
|
||||
|
@ -78,6 +77,4 @@ FLUIDSYNTH_API const char **fluid_file_renderer_get_endian_names (void);
|
|||
}
|
||||
#endif
|
||||
|
||||
/** @} */
|
||||
|
||||
#endif /* _FLUIDSYNTH_AUDIO_H */
|
||||
|
|
|
@ -36,7 +36,7 @@ extern "C" {
|
|||
* Sequencer event type enumeration.
|
||||
*/
|
||||
enum fluid_seq_event_type {
|
||||
FLUID_SEQ_NOTE = 0, /**< Note event (DOCME) */
|
||||
FLUID_SEQ_NOTE = 0, /**< Note event with duration */
|
||||
FLUID_SEQ_NOTEON, /**< Note on event */
|
||||
FLUID_SEQ_NOTEOFF, /**< Note off event */
|
||||
FLUID_SEQ_ALLSOUNDSOFF, /**< All sounds off event */
|
||||
|
@ -45,7 +45,7 @@ enum fluid_seq_event_type {
|
|||
FLUID_SEQ_PROGRAMCHANGE, /**< Program change message */
|
||||
FLUID_SEQ_PROGRAMSELECT, /**< Program select message (DOCME) */
|
||||
FLUID_SEQ_PITCHBEND, /**< Pitch bend message */
|
||||
FLUID_SEQ_PITCHWHHELSENS, /**< Pitch wheel sensitivity set message TODO: Correct spelling of this event? */
|
||||
FLUID_SEQ_PITCHWHEELSENS, /**< Pitch wheel sensitivity set message @since 1.1.0 was mispelled previously */
|
||||
FLUID_SEQ_MODULATION, /**< Modulation controller event */
|
||||
FLUID_SEQ_SUSTAIN, /**< Sustain controller event */
|
||||
FLUID_SEQ_CONTROLCHANGE, /**< MIDI control change event */
|
||||
|
@ -61,6 +61,8 @@ enum fluid_seq_event_type {
|
|||
FLUID_SEQ_LASTEVENT /**< Defines the count of event enums */
|
||||
};
|
||||
|
||||
#define FLUID_SEQ_PITCHWHHELSENS FLUID_SEQ_PITCHWHEELSENS /**< Old deprecated misspelling of #FLUID_SEQ_PITCHWHEELSENS */
|
||||
|
||||
/* Event alloc/free */
|
||||
FLUIDSYNTH_API fluid_event_t* new_fluid_event(void);
|
||||
FLUIDSYNTH_API void delete_fluid_event(fluid_event_t* evt);
|
||||
|
|
|
@ -115,13 +115,13 @@ typedef struct _fluid_gen_t
|
|||
} fluid_gen_t;
|
||||
|
||||
/**
|
||||
* Enum value for 'flags' field of #_fluid_gen_t (not really flags).
|
||||
* Enum value for 'flags' field of #fluid_gen_t (not really flags).
|
||||
*/
|
||||
enum fluid_gen_flags
|
||||
{
|
||||
GEN_UNUSED, /**< Generator value is not set */
|
||||
GEN_SET, /**< Generator value is set */
|
||||
GEN_ABS_NRPN /**< DOCME */
|
||||
GEN_ABS_NRPN /**< Generator is an absolute value */
|
||||
};
|
||||
|
||||
FLUIDSYNTH_API int fluid_gen_set_default_values(fluid_gen_t* gen);
|
||||
|
|
|
@ -41,11 +41,12 @@ extern "C" {
|
|||
* and ignores all other messages by setting the log function to
|
||||
* NULL:
|
||||
*
|
||||
* DOCME (formatting)
|
||||
* fluid_set_log_function(FLUID_PANIC, show_dialog, (void*) root_window);
|
||||
* fluid_set_log_function(FLUID_ERR, NULL, NULL);
|
||||
* fluid_set_log_function(FLUID_WARN, NULL, NULL);
|
||||
* fluid_set_log_function(FLUID_DBG, NULL, NULL);
|
||||
* @code
|
||||
* fluid_set_log_function(FLUID_PANIC, show_dialog, (void*) root_window);
|
||||
* fluid_set_log_function(FLUID_ERR, NULL, NULL);
|
||||
* fluid_set_log_function(FLUID_WARN, NULL, NULL);
|
||||
* fluid_set_log_function(FLUID_DBG, NULL, NULL);
|
||||
* @endcode
|
||||
*/
|
||||
|
||||
/**
|
||||
|
|
|
@ -56,7 +56,7 @@ FLUIDSYNTH_API int fluid_midi_event_set_sysex(fluid_midi_event_t* evt, void *dat
|
|||
* Generic callback function for MIDI events.
|
||||
* @param data User defined data pointer
|
||||
* @param event The MIDI event
|
||||
* @return DOCME
|
||||
* @return Should return #FLUID_OK on success, #FLUID_FAILED otherwise
|
||||
*
|
||||
* Will be used between
|
||||
* - MIDI driver and MIDI router
|
||||
|
@ -66,26 +66,14 @@ FLUIDSYNTH_API int fluid_midi_event_set_sysex(fluid_midi_event_t* evt, void *dat
|
|||
*/
|
||||
typedef int (*handle_midi_event_func_t)(void* data, fluid_midi_event_t* event);
|
||||
|
||||
/*
|
||||
* MIDI router
|
||||
*
|
||||
* The MIDI handler forwards incoming MIDI events to the synthesizer
|
||||
*/
|
||||
|
||||
FLUIDSYNTH_API fluid_midi_router_t* new_fluid_midi_router(fluid_settings_t* settings,
|
||||
handle_midi_event_func_t handler,
|
||||
void* event_handler_data);
|
||||
|
||||
FLUIDSYNTH_API int delete_fluid_midi_router(fluid_midi_router_t* handler);
|
||||
FLUIDSYNTH_API int fluid_midi_router_handle_midi_event(void* data, fluid_midi_event_t* event);
|
||||
FLUIDSYNTH_API int fluid_midi_dump_prerouter(void* data, fluid_midi_event_t* event);
|
||||
FLUIDSYNTH_API int fluid_midi_dump_postrouter(void* data, fluid_midi_event_t* event);
|
||||
|
||||
/*
|
||||
* MIDI driver
|
||||
*
|
||||
* The MIDI handler forwards incoming MIDI events to the synthesizer
|
||||
*/
|
||||
|
||||
FLUIDSYNTH_API
|
||||
fluid_midi_driver_t* new_fluid_midi_driver(fluid_settings_t* settings,
|
||||
|
@ -97,17 +85,14 @@ FLUIDSYNTH_API void delete_fluid_midi_driver(fluid_midi_driver_t* driver);
|
|||
FLUIDSYNTH_API void fluid_midi_driver_get_names(char* buf, size_t buflen, const char* separator);
|
||||
|
||||
|
||||
/*
|
||||
* MIDI file player
|
||||
*
|
||||
* The MIDI player allows you to play MIDI files with the FLUID Synth
|
||||
/**
|
||||
* MIDI player status enum.
|
||||
*/
|
||||
|
||||
enum fluid_player_status
|
||||
{
|
||||
FLUID_PLAYER_READY,
|
||||
FLUID_PLAYER_PLAYING,
|
||||
FLUID_PLAYER_DONE
|
||||
FLUID_PLAYER_READY, /**< Player is ready */
|
||||
FLUID_PLAYER_PLAYING, /**< Player is currently playing */
|
||||
FLUID_PLAYER_DONE /**< Player is finished playing */
|
||||
};
|
||||
|
||||
FLUIDSYNTH_API fluid_player_t* new_fluid_player(fluid_synth_t* synth);
|
||||
|
|
|
@ -27,32 +27,44 @@ extern "C" {
|
|||
#endif
|
||||
|
||||
|
||||
/*
|
||||
/**
|
||||
* @file misc.h
|
||||
* @brief Miscellaneous utility functions and defines
|
||||
*/
|
||||
|
||||
/**
|
||||
* Value that indicates success, used by most libfluidsynth functions.
|
||||
* @since 1.1.0
|
||||
*
|
||||
* Utility functions
|
||||
* NOTE: This was not publicly defined prior to libfluidsynth 1.1.0. When
|
||||
* writing code which should also be compatible with older versions, something
|
||||
* like the following can be used:
|
||||
*
|
||||
* @code
|
||||
* #include <fluidsynth.h>
|
||||
*
|
||||
* #ifndef FLUID_OK
|
||||
* #define FLUID_OK (0)
|
||||
* #define FLUID_FAILED (-1)
|
||||
* #endif
|
||||
* @endcode
|
||||
*/
|
||||
#define FLUID_OK (0)
|
||||
|
||||
/**
|
||||
* fluid_is_soundfont returns 1 if the specified filename is a
|
||||
* soundfont. It retuns 0 otherwise. The current implementation only
|
||||
* checks for the "RIFF" header in the file. It is useful only to
|
||||
* distinguish between SoundFonts and MIDI files.
|
||||
* Value that indicates failure, used by most libfluidsynth functions.
|
||||
* @since 1.1.0
|
||||
*
|
||||
* NOTE: See #FLUID_OK for more details.
|
||||
*/
|
||||
#define FLUID_FAILED (-1)
|
||||
|
||||
|
||||
FLUIDSYNTH_API int fluid_is_soundfont(char* filename);
|
||||
|
||||
/**
|
||||
* fluid_is_midifile returns 1 if the specified filename is a MIDI
|
||||
* file. It retuns 0 otherwise. The current implementation only checks
|
||||
* for the "MThd" header in the file.
|
||||
*/
|
||||
FLUIDSYNTH_API int fluid_is_midifile(char* filename);
|
||||
|
||||
|
||||
|
||||
|
||||
#ifdef WIN32
|
||||
/** Set the handle to the instance of the application on the Windows
|
||||
platform. The handle is needed to open DirectSound. */
|
||||
FLUIDSYNTH_API void* fluid_get_hinstance(void);
|
||||
FLUIDSYNTH_API void fluid_set_hinstance(void* hinstance);
|
||||
#endif
|
||||
|
|
|
@ -25,22 +25,24 @@
|
|||
extern "C" {
|
||||
#endif
|
||||
|
||||
/* Modulator-related definitions */
|
||||
/**
|
||||
* @file mod.h
|
||||
* @brief SoundFont modulator functions and constants.
|
||||
*/
|
||||
|
||||
/* Maximum number of modulators in a voice */
|
||||
#define FLUID_NUM_MOD 64
|
||||
#define FLUID_NUM_MOD 64 /**< Maximum number of modulators in a voice */
|
||||
|
||||
/*
|
||||
* fluid_mod_t
|
||||
*/
|
||||
/**
|
||||
* Modulator structure. See SoundFont 2.04 PDF section 8.2.
|
||||
*/
|
||||
struct _fluid_mod_t
|
||||
{
|
||||
unsigned char dest;
|
||||
unsigned char src1;
|
||||
unsigned char flags1;
|
||||
unsigned char src2;
|
||||
unsigned char flags2;
|
||||
double amount;
|
||||
unsigned char dest; /**< Destination generator to control */
|
||||
unsigned char src1; /**< Source controller 1 */
|
||||
unsigned char flags1; /**< Source controller 1 flags */
|
||||
unsigned char src2; /**< Source controller 2 */
|
||||
unsigned char flags2; /**< Source controller 2 flags */
|
||||
double amount; /**< Multiplier amount */
|
||||
/* The 'next' field allows to link modulators into a list. It is
|
||||
* not used in fluid_voice.c, there each voice allocates memory for a
|
||||
* fixed number of modulators. Since there may be a huge number of
|
||||
|
@ -49,44 +51,45 @@ struct _fluid_mod_t
|
|||
fluid_mod_t * next;
|
||||
};
|
||||
|
||||
/* Flags telling the polarity of a modulator. Compare with SF2.01
|
||||
section 8.2. Note: The numbers of the bits are different! (for
|
||||
example: in the flags of a SF modulator, the polarity bit is bit
|
||||
nr. 9) */
|
||||
/**
|
||||
* Flags defining the polarity and mapping function of a modulator source.
|
||||
* Compare with SoundFont 2.04 PDF section 8.2.
|
||||
*
|
||||
* Note: The numbers of the bits are different! (for example: in the flags of
|
||||
* a SoundFont modulator, the polarity bit is bit #9).
|
||||
*/
|
||||
enum fluid_mod_flags
|
||||
{
|
||||
FLUID_MOD_POSITIVE = 0,
|
||||
FLUID_MOD_NEGATIVE = 1,
|
||||
FLUID_MOD_UNIPOLAR = 0,
|
||||
FLUID_MOD_BIPOLAR = 2,
|
||||
FLUID_MOD_LINEAR = 0,
|
||||
FLUID_MOD_CONCAVE = 4,
|
||||
FLUID_MOD_CONVEX = 8,
|
||||
FLUID_MOD_SWITCH = 12,
|
||||
FLUID_MOD_GC = 0,
|
||||
FLUID_MOD_CC = 16
|
||||
FLUID_MOD_POSITIVE = 0, /**< Mapping function is positive */
|
||||
FLUID_MOD_NEGATIVE = 1, /**< Mapping function is negative */
|
||||
FLUID_MOD_UNIPOLAR = 0, /**< Mapping function is unipolar */
|
||||
FLUID_MOD_BIPOLAR = 2, /**< Mapping function is bipolar */
|
||||
FLUID_MOD_LINEAR = 0, /**< Linear mapping function */
|
||||
FLUID_MOD_CONCAVE = 4, /**< Concave mapping function */
|
||||
FLUID_MOD_CONVEX = 8, /**< Convex mapping function */
|
||||
FLUID_MOD_SWITCH = 12, /**< Switch (on/off) mapping function */
|
||||
FLUID_MOD_GC = 0, /**< General controller */
|
||||
FLUID_MOD_CC = 16 /**< MIDI CC controller */
|
||||
};
|
||||
|
||||
/* Flags telling the source of a modulator. This corresponds to
|
||||
* SF2.01 section 8.2.1 */
|
||||
/**
|
||||
* Flags indicating the source of a modulator (if #FLUID_MOD_GC). This
|
||||
* corresponds to SoundFont 2.04 PDF section 8.2.1
|
||||
*/
|
||||
enum fluid_mod_src
|
||||
{
|
||||
FLUID_MOD_NONE = 0,
|
||||
FLUID_MOD_VELOCITY = 2,
|
||||
FLUID_MOD_KEY = 3,
|
||||
FLUID_MOD_KEYPRESSURE = 10,
|
||||
FLUID_MOD_CHANNELPRESSURE = 13,
|
||||
FLUID_MOD_PITCHWHEEL = 14,
|
||||
FLUID_MOD_PITCHWHEELSENS = 16
|
||||
FLUID_MOD_NONE = 0, /**< No source controller */
|
||||
FLUID_MOD_VELOCITY = 2, /**< MIDI note-on velocity */
|
||||
FLUID_MOD_KEY = 3, /**< MIDI note-on note number */
|
||||
FLUID_MOD_KEYPRESSURE = 10, /**< MIDI key pressure */
|
||||
FLUID_MOD_CHANNELPRESSURE = 13, /**< MIDI channel pressure */
|
||||
FLUID_MOD_PITCHWHEEL = 14, /**< Pitch wheel */
|
||||
FLUID_MOD_PITCHWHEELSENS = 16 /**< Pitch wheel sensitivity */
|
||||
};
|
||||
|
||||
/* Allocates memory for a new modulator */
|
||||
FLUIDSYNTH_API fluid_mod_t * fluid_mod_new(void);
|
||||
|
||||
/* Frees the modulator */
|
||||
FLUIDSYNTH_API fluid_mod_t* fluid_mod_new(void);
|
||||
FLUIDSYNTH_API void fluid_mod_delete(fluid_mod_t * mod);
|
||||
|
||||
|
||||
FLUIDSYNTH_API void fluid_mod_set_source1(fluid_mod_t* mod, int src, int flags);
|
||||
FLUIDSYNTH_API void fluid_mod_set_source2(fluid_mod_t* mod, int src, int flags);
|
||||
FLUIDSYNTH_API void fluid_mod_set_dest(fluid_mod_t* mod, int dst);
|
||||
|
@ -99,9 +102,6 @@ FLUIDSYNTH_API int fluid_mod_get_flags2(fluid_mod_t* mod);
|
|||
FLUIDSYNTH_API int fluid_mod_get_dest(fluid_mod_t* mod);
|
||||
FLUIDSYNTH_API double fluid_mod_get_amount(fluid_mod_t* mod);
|
||||
|
||||
|
||||
/* Determines, if two modulators are 'identical' (all parameters
|
||||
except the amount match) */
|
||||
FLUIDSYNTH_API int fluid_mod_test_identity(fluid_mod_t * mod1, fluid_mod_t * mod2);
|
||||
|
||||
|
||||
|
|
|
@ -18,6 +18,8 @@
|
|||
* 02111-1307, USA
|
||||
*/
|
||||
|
||||
/* RAM SoundFonts: October 2002 - Antoine Schmitt */
|
||||
|
||||
#ifndef _FLUIDSYNTH_RAMSFONT_H
|
||||
#define _FLUIDSYNTH_RAMSFONT_H
|
||||
|
||||
|
@ -25,82 +27,39 @@
|
|||
extern "C" {
|
||||
#endif
|
||||
|
||||
|
||||
/********************************************************************************/
|
||||
/********************************************************************************/
|
||||
/* ram soundfonts:
|
||||
October 2002 - Antoine Schmitt
|
||||
|
||||
ram soundfonts live in ram. The samples are loaded from files
|
||||
or from RAM. A minimal API manages a soundFont structure,
|
||||
with presets, each preset having only one preset-zone, which
|
||||
instrument has potentially many instrument-zones. No global
|
||||
zones, and nor generator nor modulator other than the default
|
||||
ones are permitted. This may be extensible in the future.
|
||||
*/
|
||||
/********************************************************************************/
|
||||
/********************************************************************************/
|
||||
|
||||
/*
|
||||
We are not using the sfloader protocol, as we need more arguments
|
||||
than what it provides.
|
||||
*/
|
||||
|
||||
/** Creates a fluid_sfont_t wrapping an fluid_ramsfont_t */
|
||||
FLUIDSYNTH_API fluid_sfont_t* fluid_ramsfont_create_sfont(void);
|
||||
|
||||
/***********************
|
||||
* ramsfont specific API
|
||||
***********************/
|
||||
FLUIDSYNTH_API int fluid_ramsfont_set_name(fluid_ramsfont_t* sfont, char * name);
|
||||
|
||||
/* Creates one instrument zone for the sample inside the preset defined
|
||||
* by bank/num
|
||||
* \returns 0 if success
|
||||
/**
|
||||
* @file ramsfont.h
|
||||
* @brief API for creating and managing SoundFont instruments in RAM.
|
||||
*
|
||||
* RAM SoundFonts live in ram. The samples are loaded from files
|
||||
* or from RAM. A minimal API manages a soundFont structure,
|
||||
* with presets, each preset having only one preset-zone, which
|
||||
* instrument has potentially many instrument-zones. No global
|
||||
* zones, and nor generator nor modulator other than the default
|
||||
* ones are permitted. This may be extensible in the future.
|
||||
*/
|
||||
|
||||
FLUIDSYNTH_API fluid_sfont_t* fluid_ramsfont_create_sfont(void);
|
||||
FLUIDSYNTH_API int fluid_ramsfont_set_name(fluid_ramsfont_t* sfont, char * name);
|
||||
FLUIDSYNTH_API
|
||||
int fluid_ramsfont_add_izone(fluid_ramsfont_t* sfont,
|
||||
unsigned int bank, unsigned int num, fluid_sample_t* sample,
|
||||
int lokey, int hikey);
|
||||
|
||||
/* Removes the instrument zone corresponding to bank/num and to the sample
|
||||
* \returns 0 if success
|
||||
*/
|
||||
FLUIDSYNTH_API
|
||||
int fluid_ramsfont_remove_izone(fluid_ramsfont_t* sfont,
|
||||
unsigned int bank, unsigned int num, fluid_sample_t* sample);
|
||||
|
||||
/* Sets a generator on an instrument zone
|
||||
* \returns 0 if success
|
||||
*/
|
||||
FLUIDSYNTH_API
|
||||
int fluid_ramsfont_izone_set_gen(fluid_ramsfont_t* sfont,
|
||||
unsigned int bank, unsigned int num, fluid_sample_t* sample,
|
||||
int gen_type, float value);
|
||||
|
||||
/* Utility : sets the loop start/end values
|
||||
* \on = 0 or 1; if 0, loopstart and loopend are not used
|
||||
* \loopstart and loopend are floats, in frames
|
||||
* \loopstart is counted from frame 0
|
||||
* \loopend is counted from the last frame, thus is < 0
|
||||
* \returns 0 if success
|
||||
*/
|
||||
FLUIDSYNTH_API
|
||||
int fluid_ramsfont_izone_set_loop(fluid_ramsfont_t* sfont,
|
||||
unsigned int bank, unsigned int num, fluid_sample_t* sample,
|
||||
int on, float loopstart, float loopend);
|
||||
|
||||
/***************************************
|
||||
* sample_t specific API for ramsfont
|
||||
***************************************/
|
||||
FLUIDSYNTH_API fluid_sample_t* new_fluid_ramsample(void);
|
||||
FLUIDSYNTH_API int delete_fluid_ramsample(fluid_sample_t* sample);
|
||||
FLUIDSYNTH_API int fluid_sample_set_name(fluid_sample_t* sample, char * name);
|
||||
|
||||
/* Sets the sound data of the sample
|
||||
* Warning : if copy_data is FALSE, data should have 8 unused frames at start
|
||||
* and 8 unused frames at the end.
|
||||
*/
|
||||
FLUIDSYNTH_API
|
||||
int fluid_sample_set_sound_data(fluid_sample_t* sample, short *data,
|
||||
unsigned int nbframes, short copy_data, int rootkey);
|
||||
|
|
|
@ -25,81 +25,39 @@
|
|||
extern "C" {
|
||||
#endif
|
||||
|
||||
/**
|
||||
* @file seq.h
|
||||
* @brief MIDI event sequencer.
|
||||
*/
|
||||
|
||||
typedef void (*fluid_event_callback_t)(unsigned int time, fluid_event_t* event,
|
||||
fluid_sequencer_t* seq, void* data);
|
||||
|
||||
|
||||
/** Allocate a new sequencer structure */
|
||||
FLUIDSYNTH_API fluid_sequencer_t* new_fluid_sequencer(void);
|
||||
FLUIDSYNTH_API fluid_sequencer_t* new_fluid_sequencer2(int useSystemTimer);
|
||||
|
||||
/** Free the sequencer structure */
|
||||
FLUIDSYNTH_API fluid_sequencer_t* new_fluid_sequencer2(int use_system_timer);
|
||||
FLUIDSYNTH_API void delete_fluid_sequencer(fluid_sequencer_t* seq);
|
||||
|
||||
|
||||
FLUIDSYNTH_API int fluid_sequencer_get_useSystemTimer(fluid_sequencer_t* seq);
|
||||
|
||||
/** clients can be sources or destinations of events. These functions ensure a unique ID for any
|
||||
source or dest, for filtering purposes.
|
||||
sources only dont need to register a callback.
|
||||
*/
|
||||
|
||||
/** Register a client. The registration returns a unique client ID (-1 if error) */
|
||||
FLUIDSYNTH_API int fluid_sequencer_get_use_system_timer(fluid_sequencer_t* seq);
|
||||
FLUIDSYNTH_API
|
||||
short fluid_sequencer_register_client(fluid_sequencer_t* seq, char* name,
|
||||
fluid_event_callback_t callback, void* data);
|
||||
|
||||
/** Unregister a previously registered client. */
|
||||
FLUIDSYNTH_API void fluid_sequencer_unregister_client(fluid_sequencer_t* seq, short id);
|
||||
|
||||
/** Returns the number of register clients. */
|
||||
FLUIDSYNTH_API int fluid_sequencer_count_clients(fluid_sequencer_t* seq);
|
||||
|
||||
/** Returns the id of a registered client (-1 if non existing) */
|
||||
FLUIDSYNTH_API short fluid_sequencer_get_client_id(fluid_sequencer_t* seq, int index);
|
||||
|
||||
/** Returns the name of a registered client, given its id. */
|
||||
FLUIDSYNTH_API char* fluid_sequencer_get_client_name(fluid_sequencer_t* seq, int id);
|
||||
|
||||
/** Returns 1 if client is a destination (has a callback) */
|
||||
FLUIDSYNTH_API int fluid_sequencer_client_is_dest(fluid_sequencer_t* seq, int id);
|
||||
|
||||
/** Advance sequencer. Do not use if you created the sequencer with useSystemTimer enabled. */
|
||||
FLUIDSYNTH_API void fluid_sequencer_process(fluid_sequencer_t* seq, unsigned int msec);
|
||||
|
||||
/** Sending an event immediately. */
|
||||
FLUIDSYNTH_API void fluid_sequencer_send_now(fluid_sequencer_t* seq, fluid_event_t* evt);
|
||||
|
||||
|
||||
/** Schedule an event for later sending. If absolute is 0, the time of
|
||||
the event will be offset with the current tick of the
|
||||
sequencer. If absolute is different from 0, the time will assumed
|
||||
to be absolute (starting from the creation of the sequencer).
|
||||
MAKES A COPY */
|
||||
FLUIDSYNTH_API
|
||||
int fluid_sequencer_send_at(fluid_sequencer_t* seq, fluid_event_t* evt,
|
||||
unsigned int time, int absolute);
|
||||
|
||||
/** Remove events from the event queue. The events can be filtered on
|
||||
the source, the destination, and the type of the event. To avoid
|
||||
filtering, set either source, dest, or type to -1. */
|
||||
FLUIDSYNTH_API
|
||||
void fluid_sequencer_remove_events(fluid_sequencer_t* seq, short source, short dest, int type);
|
||||
|
||||
|
||||
/** Get the current tick */
|
||||
FLUIDSYNTH_API unsigned int fluid_sequencer_get_tick(fluid_sequencer_t* seq);
|
||||
|
||||
/** Set the conversion from tick to absolute time. scale should be
|
||||
expressed as ticks per second. */
|
||||
FLUIDSYNTH_API void fluid_sequencer_set_time_scale(fluid_sequencer_t* seq, double scale);
|
||||
|
||||
/** Set the conversion from tick to absolute time (ticks per
|
||||
second). */
|
||||
FLUIDSYNTH_API double fluid_sequencer_get_time_scale(fluid_sequencer_t* seq);
|
||||
|
||||
// compile in internal traceing functions
|
||||
// Compile in internal traceing functions
|
||||
#define FLUID_SEQ_WITH_TRACE 0
|
||||
|
||||
#if FLUID_SEQ_WITH_TRACE
|
||||
|
|
|
@ -27,15 +27,14 @@
|
|||
extern "C" {
|
||||
#endif
|
||||
|
||||
/** registers fluidsynth as a client of the given sequencer.
|
||||
The fluidsynth is registered with the name "fluidsynth".
|
||||
|
||||
\returns the fluidsynth destID.
|
||||
*/
|
||||
/**
|
||||
* @file seqbind.h
|
||||
* @brief FIXME Not sure why this is separate from seq.h.
|
||||
*/
|
||||
|
||||
FLUIDSYNTH_API
|
||||
short fluid_sequencer_register_fluidsynth(fluid_sequencer_t* seq, fluid_synth_t* synth);
|
||||
|
||||
int
|
||||
FLUIDSYNTH_API int
|
||||
fluid_sequencer_add_midi_event_to_buffer(void* data, fluid_midi_event_t* event);
|
||||
|
||||
|
||||
|
|
|
@ -49,15 +49,16 @@ extern "C" {
|
|||
* }
|
||||
* @endcode
|
||||
* @sa @ref CreatingSettings
|
||||
* @{
|
||||
*/
|
||||
|
||||
/** Hint FLUID_HINT_BOUNDED_BELOW indicates that the LowerBound field
|
||||
of the FLUID_PortRangeHint should be considered meaningful. The
|
||||
value in this field should be considered the (inclusive) lower
|
||||
bound of the valid range. If FLUID_HINT_SAMPLE_RATE is also
|
||||
specified then the value of LowerBound should be multiplied by the
|
||||
sample rate. */
|
||||
/**
|
||||
* Hint FLUID_HINT_BOUNDED_BELOW indicates that the LowerBound field
|
||||
* of the FLUID_PortRangeHint should be considered meaningful. The
|
||||
* value in this field should be considered the (inclusive) lower
|
||||
* bound of the valid range. If FLUID_HINT_SAMPLE_RATE is also
|
||||
* specified then the value of LowerBound should be multiplied by the
|
||||
* sample rate.
|
||||
*/
|
||||
#define FLUID_HINT_BOUNDED_BELOW 0x1
|
||||
|
||||
/** Hint FLUID_HINT_BOUNDED_ABOVE indicates that the UpperBound field
|
||||
|
@ -68,38 +69,45 @@ extern "C" {
|
|||
sample rate. */
|
||||
#define FLUID_HINT_BOUNDED_ABOVE 0x2
|
||||
|
||||
/** Hint FLUID_HINT_TOGGLED indicates that the data item should be
|
||||
considered a Boolean toggle. Data less than or equal to zero should
|
||||
be considered `off' or `false,' and data above zero should be
|
||||
considered `on' or `true.' FLUID_HINT_TOGGLED may not be used in
|
||||
conjunction with any other hint except FLUID_HINT_DEFAULT_0 or
|
||||
FLUID_HINT_DEFAULT_1. */
|
||||
/**
|
||||
* Hint FLUID_HINT_TOGGLED indicates that the data item should be
|
||||
* considered a Boolean toggle. Data less than or equal to zero should
|
||||
* be considered `off' or `false,' and data above zero should be
|
||||
* considered `on' or `true.' FLUID_HINT_TOGGLED may not be used in
|
||||
* conjunction with any other hint.
|
||||
*/
|
||||
#define FLUID_HINT_TOGGLED 0x4
|
||||
|
||||
/** Hint FLUID_HINT_SAMPLE_RATE indicates that any bounds specified
|
||||
should be interpreted as multiples of the sample rate. For
|
||||
instance, a frequency range from 0Hz to the Nyquist frequency (half
|
||||
the sample rate) could be requested by this hint in conjunction
|
||||
with LowerBound = 0 and UpperBound = 0.5. Hosts that support bounds
|
||||
at all must support this hint to retain meaning. */
|
||||
/**
|
||||
* Hint FLUID_HINT_SAMPLE_RATE indicates that any bounds specified
|
||||
* should be interpreted as multiples of the sample rate. For
|
||||
* instance, a frequency range from 0Hz to the Nyquist frequency (half
|
||||
* the sample rate) could be requested by this hint in conjunction
|
||||
* with LowerBound = 0 and UpperBound = 0.5. Hosts that support bounds
|
||||
* at all must support this hint to retain meaning.
|
||||
*/
|
||||
#define FLUID_HINT_SAMPLE_RATE 0x8
|
||||
|
||||
/** Hint FLUID_HINT_LOGARITHMIC indicates that it is likely that the
|
||||
user will find it more intuitive to view values using a logarithmic
|
||||
scale. This is particularly useful for frequencies and gains. */
|
||||
/**
|
||||
* Hint FLUID_HINT_LOGARITHMIC indicates that it is likely that the
|
||||
* user will find it more intuitive to view values using a logarithmic
|
||||
* scale. This is particularly useful for frequencies and gains.
|
||||
*/
|
||||
#define FLUID_HINT_LOGARITHMIC 0x10
|
||||
|
||||
/** Hint FLUID_HINT_INTEGER indicates that a user interface would
|
||||
probably wish to provide a stepped control taking only integer
|
||||
values. Any bounds set should be slightly wider than the actual
|
||||
integer range required to avoid floating point rounding errors. For
|
||||
instance, the integer set {0,1,2,3} might be described as [-0.1,
|
||||
3.1]. */
|
||||
/**
|
||||
* Hint FLUID_HINT_INTEGER indicates that a user interface would
|
||||
* probably wish to provide a stepped control taking only integer
|
||||
* values. Any bounds set should be slightly wider than the actual
|
||||
* integer range required to avoid floating point rounding errors. For
|
||||
* instance, the integer set {0,1,2,3} might be described as [-0.1,
|
||||
* 3.1].
|
||||
*/
|
||||
#define FLUID_HINT_INTEGER 0x20
|
||||
|
||||
|
||||
#define FLUID_HINT_FILENAME 0x01
|
||||
#define FLUID_HINT_OPTIONLIST 0x02
|
||||
#define FLUID_HINT_FILENAME 0x01 /**< Setting is a file name */
|
||||
#define FLUID_HINT_OPTIONLIST 0x02 /**< Setting is a list of string options */
|
||||
|
||||
|
||||
/**
|
||||
|
@ -110,11 +118,11 @@ extern "C" {
|
|||
* function fluid_settings_get_type()
|
||||
*/
|
||||
enum fluid_types_enum {
|
||||
FLUID_NO_TYPE = -1,//!< Undefined type
|
||||
FLUID_NUM_TYPE, //!< Numeric (double)
|
||||
FLUID_INT_TYPE, //!< Integer
|
||||
FLUID_STR_TYPE, //!< String
|
||||
FLUID_SET_TYPE //!< Set of values
|
||||
FLUID_NO_TYPE = -1, /**< Undefined type */
|
||||
FLUID_NUM_TYPE, /**< Numeric (double) */
|
||||
FLUID_INT_TYPE, /**< Integer */
|
||||
FLUID_STR_TYPE, /**< String */
|
||||
FLUID_SET_TYPE /**< Set of values */
|
||||
};
|
||||
|
||||
|
||||
|
@ -176,6 +184,9 @@ void fluid_settings_getint_range(fluid_settings_t* settings, char* name,
|
|||
|
||||
/**
|
||||
* Callback function type used with fluid_settings_foreach_option()
|
||||
* @param data User defined data pointer
|
||||
* @param name Setting name
|
||||
* @param option A string option for this setting (iterates through the list)
|
||||
*/
|
||||
typedef void (*fluid_settings_foreach_option_t)(void* data, char* name, char* option);
|
||||
|
||||
|
@ -192,8 +203,11 @@ int fluid_settings_option_count (fluid_settings_t* settings, char* name);
|
|||
|
||||
/**
|
||||
* Callback function type used with fluid_settings_foreach()
|
||||
* @param data User defined data pointer
|
||||
* @param name Setting name
|
||||
* @param type Setting type (#fluid_types_enum)
|
||||
*/
|
||||
typedef void (*fluid_settings_foreach_t)(void* data, char* s, int type);
|
||||
typedef void (*fluid_settings_foreach_t)(void* data, char* name, int type);
|
||||
|
||||
FLUIDSYNTH_API
|
||||
void fluid_settings_foreach(fluid_settings_t* settings, void* data,
|
||||
|
@ -206,6 +220,4 @@ void fluid_settings_foreach_alpha(fluid_settings_t* settings, void* data,
|
|||
}
|
||||
#endif
|
||||
|
||||
/** @} */
|
||||
|
||||
#endif /* _FLUIDSYNTH_SETTINGS_H */
|
||||
|
|
|
@ -26,163 +26,252 @@ extern "C" {
|
|||
#endif
|
||||
|
||||
|
||||
|
||||
/**
|
||||
*
|
||||
* SoundFont plugins
|
||||
*
|
||||
* It is possible to add new SoundFont loaders to the
|
||||
* synthesizer. The API uses a couple of "interfaces" (structures
|
||||
* with callback functions): fluid_sfloader_t, fluid_sfont_t, and
|
||||
* fluid_preset_t.
|
||||
*
|
||||
* To add a new SoundFont loader to the synthesizer, call
|
||||
* fluid_synth_add_sfloader() and pass a pointer to an
|
||||
* fluid_sfloader_t structure. The important callback function in
|
||||
* this structure is "load", which should try to load a file and
|
||||
* returns a fluid_sfont_t structure, or NULL if it fails.
|
||||
*
|
||||
* The fluid_sfont_t structure contains a callback to obtain the
|
||||
* name of the soundfont. It contains two functions to iterate
|
||||
* though the contained presets, and one function to obtain a
|
||||
* preset corresponding to a bank and preset number. This
|
||||
* function should return an fluid_preset_t structure.
|
||||
*
|
||||
* The fluid_preset_t structure contains some functions to obtain
|
||||
* information from the preset (name, bank, number). The most
|
||||
* important callback is the noteon function. The noteon function
|
||||
* should call fluid_synth_alloc_voice() for every sample that has
|
||||
* to be played. fluid_synth_alloc_voice() expects a pointer to a
|
||||
* fluid_sample_t structure and returns a pointer to the opaque
|
||||
* fluid_voice_t structure. To set or increments the values of a
|
||||
* generator, use fluid_voice_gen_{set,incr}. When you are
|
||||
* finished initializing the voice call fluid_voice_start() to
|
||||
* start playing the synthesis voice.
|
||||
* */
|
||||
|
||||
enum {
|
||||
FLUID_PRESET_SELECTED,
|
||||
FLUID_PRESET_UNSELECTED,
|
||||
FLUID_SAMPLE_DONE
|
||||
};
|
||||
|
||||
|
||||
/*
|
||||
* fluid_sfloader_t
|
||||
/**
|
||||
* @file sfont.h
|
||||
* @brief SoundFont plugins
|
||||
*
|
||||
* It is possible to add new SoundFont loaders to the
|
||||
* synthesizer. The API uses a couple of "interfaces" (structures
|
||||
* with callback functions): #fluid_sfloader_t, #fluid_sfont_t, and
|
||||
* #fluid_preset_t. This API allows for virtual SoundFont files to be loaded
|
||||
* and synthesized, which may not actually be SoundFont files, as long as they
|
||||
* can be represented by the SoundFont synthesis model.
|
||||
*
|
||||
* To add a new SoundFont loader to the synthesizer, call
|
||||
* fluid_synth_add_sfloader() and pass a pointer to an
|
||||
* fluid_sfloader_t structure. The important callback function in
|
||||
* this structure is "load", which should try to load a file and
|
||||
* returns a #fluid_sfont_t structure, or NULL if it fails.
|
||||
*
|
||||
* The #fluid_sfont_t structure contains a callback to obtain the
|
||||
* name of the SoundFont. It contains two functions to iterate
|
||||
* though the contained presets, and one function to obtain a
|
||||
* preset corresponding to a bank and preset number. This
|
||||
* function should return a #fluid_preset_t structure.
|
||||
*
|
||||
* The #fluid_preset_t structure contains some functions to obtain
|
||||
* information from the preset (name, bank, number). The most
|
||||
* important callback is the noteon function. The noteon function
|
||||
* should call fluid_synth_alloc_voice() for every sample that has
|
||||
* to be played. fluid_synth_alloc_voice() expects a pointer to a
|
||||
* #fluid_sample_t structure and returns a pointer to the opaque
|
||||
* #fluid_voice_t structure. To set or increment the values of a
|
||||
* generator, use fluid_voice_gen_set() or fluid_voice_gen_incr(). When you are
|
||||
* finished initializing the voice call fluid_voice_start() to
|
||||
* start playing the synthesis voice.
|
||||
*/
|
||||
|
||||
struct _fluid_sfloader_t {
|
||||
/** Private data */
|
||||
void* data;
|
||||
|
||||
/** The free must free the memory allocated for the loader in
|
||||
* addition to any private data. It should return 0 if no error
|
||||
* occured, non-zero otherwise.*/
|
||||
int (*free)(fluid_sfloader_t* loader);
|
||||
|
||||
/** Load a file. Returns NULL if an error occured. */
|
||||
fluid_sfont_t* (*load)(fluid_sfloader_t* loader, const char* filename);
|
||||
/**
|
||||
* Some notification enums for presets and samples.
|
||||
*/
|
||||
enum {
|
||||
FLUID_PRESET_SELECTED, /**< Preset selected notify */
|
||||
FLUID_PRESET_UNSELECTED, /**< Preset unselected notify */
|
||||
FLUID_SAMPLE_DONE /**< Sample no longer needed notify */
|
||||
};
|
||||
|
||||
|
||||
/*
|
||||
* fluid_sfont_t
|
||||
/**
|
||||
* SoundFont loader structure.
|
||||
*/
|
||||
struct _fluid_sfloader_t {
|
||||
void* data; /**< User defined data pointer */
|
||||
|
||||
/**
|
||||
* The free method should free the memory allocated for the loader in
|
||||
* addition to any private data.
|
||||
* @param loader SoundFont loader
|
||||
* @return Should return 0 if no error occured, non-zero otherwise
|
||||
*/
|
||||
int (*free)(fluid_sfloader_t* loader);
|
||||
|
||||
/**
|
||||
* Method to load an instrument file (does not actually need to be a real file name,
|
||||
* could be another type of string identifier that the \a loader understands).
|
||||
* @param loader SoundFont loader
|
||||
* @param filename File name or other string identifier
|
||||
* @return The loaded instrument file (SoundFont) or NULL if an error occured.
|
||||
*/
|
||||
fluid_sfont_t* (*load)(fluid_sfloader_t* loader, const char* filename);
|
||||
};
|
||||
|
||||
/**
|
||||
* Virtual SoundFont instance structure.
|
||||
*/
|
||||
struct _fluid_sfont_t {
|
||||
void* data;
|
||||
unsigned int id;
|
||||
void* data; /**< User defined data */
|
||||
unsigned int id; /**< SoundFont ID */
|
||||
|
||||
/** The 'free' callback function should return 0 when it was able to
|
||||
free all resources. It should return a non-zero value if some of
|
||||
the samples could not be freed because they are still in use. */
|
||||
/**
|
||||
* Method to free a virtual SoundFont bank.
|
||||
* @param sfont Virtual SoundFont to free.
|
||||
* @return Should return 0 when it was able to free all resources or non-zero
|
||||
* if some of the samples could not be freed because they are still in use,
|
||||
* in which case the free will be tried again later, until success.
|
||||
*/
|
||||
int (*free)(fluid_sfont_t* sfont);
|
||||
|
||||
/** Return the name of the sfont */
|
||||
/**
|
||||
* Method to return the name of a virtual SoundFont.
|
||||
* @param sfont Virtual SoundFont
|
||||
* @return The name of the virtual SoundFont.
|
||||
*/
|
||||
char* (*get_name)(fluid_sfont_t* sfont);
|
||||
|
||||
/** Return the preset with the specified bank and preset number. All
|
||||
* the fields, including the 'sfont' field, should * be filled
|
||||
* in. If the preset cannot be found, the function returns NULL. */
|
||||
/**
|
||||
* Get a virtual SoundFont preset by bank and program numbers.
|
||||
* @param sfont Virtual SoundFont
|
||||
* @param bank MIDI bank number (0-16384)
|
||||
* @param prenum MIDI preset number (0-127)
|
||||
* @return Should return an allocated virtual preset or NULL if it could not
|
||||
* be found.
|
||||
*/
|
||||
fluid_preset_t* (*get_preset)(fluid_sfont_t* sfont, unsigned int bank, unsigned int prenum);
|
||||
|
||||
/**
|
||||
* Start virtual SoundFont preset iteration method.
|
||||
* @param sfont Virtual SoundFont
|
||||
*
|
||||
* Starts/re-starts virtual preset iteration in a SoundFont.
|
||||
*/
|
||||
void (*iteration_start)(fluid_sfont_t* sfont);
|
||||
|
||||
/* return 0 when no more presets are available, 1 otherwise */
|
||||
/**
|
||||
* Virtual SoundFont preset iteration function.
|
||||
* @param sfont Virtual SoundFont
|
||||
* @param preset Caller supplied preset to fill in with current preset information
|
||||
* @return 0 when no more presets are available, 1 otherwise
|
||||
*
|
||||
* Should store preset information to the caller supplied \a preset structure
|
||||
* and advance the internal iteration state to the next preset for subsequent
|
||||
* calls.
|
||||
*/
|
||||
int (*iteration_next)(fluid_sfont_t* sfont, fluid_preset_t* preset);
|
||||
};
|
||||
|
||||
#define fluid_sfont_get_id(_sf) ((_sf)->id)
|
||||
|
||||
|
||||
/*
|
||||
* fluid_preset_t
|
||||
/**
|
||||
* Virtual SoundFont preset.
|
||||
*/
|
||||
|
||||
struct _fluid_preset_t {
|
||||
void* data;
|
||||
fluid_sfont_t* sfont;
|
||||
void* data; /**< User supplied data */
|
||||
fluid_sfont_t* sfont; /**< Parent virtual SoundFont */
|
||||
|
||||
/**
|
||||
* Method to free a virtual SoundFont preset.
|
||||
* @param preset Virtual SoundFont preset
|
||||
* @return Should return 0
|
||||
*/
|
||||
int (*free)(fluid_preset_t* preset);
|
||||
|
||||
/**
|
||||
* Method to get a virtual SoundFont preset name.
|
||||
* @param preset Virtual SoundFont preset
|
||||
* @return Should return the name of the preset. The returned string must be
|
||||
* valid for the duration of the virtual preset (or the duration of the
|
||||
* SoundFont, in the case of preset iteration).
|
||||
*/
|
||||
char* (*get_name)(fluid_preset_t* preset);
|
||||
|
||||
/**
|
||||
* Method to get a virtual SoundFont preset MIDI bank number.
|
||||
* @param preset Virtual SoundFont preset
|
||||
* @param return The bank number of the preset
|
||||
*/
|
||||
int (*get_banknum)(fluid_preset_t* preset);
|
||||
|
||||
/**
|
||||
* Method to get a virtual SoundFont preset MIDI program number.
|
||||
* @param preset Virtual SoundFont preset
|
||||
* @param return The program number of the preset
|
||||
*/
|
||||
int (*get_num)(fluid_preset_t* preset);
|
||||
|
||||
/** handle a noteon event. Returns 0 if no error occured. */
|
||||
/**
|
||||
* Method to handle a noteon event (synthesize the instrument).
|
||||
* @param preset Virtual SoundFont preset
|
||||
* @param synth Synthesizer instance
|
||||
* @param chan MIDI channel number of the note on event
|
||||
* @param key MIDI note number (0-127)
|
||||
* @param vel MIDI velocity (0-127)
|
||||
* @return #FLUID_OK on success (0) or #FLUID_FAILED (-1) otherwise
|
||||
*
|
||||
* This method may be called from within synthesis context and therefore
|
||||
* should be as efficient as possible and not perform any operations considered
|
||||
* bad for realtime audio output (memory allocations and other OS calls).
|
||||
*
|
||||
* Call fluid_synth_alloc_voice() for every sample that has
|
||||
* to be played. fluid_synth_alloc_voice() expects a pointer to a
|
||||
* #fluid_sample_t structure and returns a pointer to the opaque
|
||||
* #fluid_voice_t structure. To set or increment the values of a
|
||||
* generator, use fluid_voice_gen_set() or fluid_voice_gen_incr(). When you are
|
||||
* finished initializing the voice call fluid_voice_start() to
|
||||
* start playing the synthesis voice. Starting with FluidSynth 1.1.0 all voices
|
||||
* created will be started at the same time.
|
||||
*/
|
||||
int (*noteon)(fluid_preset_t* preset, fluid_synth_t* synth, int chan, int key, int vel);
|
||||
|
||||
/** Implement this function if the preset needs to be notified about
|
||||
preset select and unselect events. */
|
||||
/**
|
||||
* Virtual SoundFont preset notify method.
|
||||
* @param preset Virtual SoundFont preset
|
||||
* @param reason #FLUID_PRESET_SELECTED or #FLUID_PRESET_UNSELECTED
|
||||
* @param chan MIDI channel number
|
||||
* @return Should return #FLUID_OK
|
||||
*
|
||||
* Implement this optional method if the preset needs to be notified about
|
||||
* preset select and unselect events.
|
||||
*
|
||||
* This method may be called from within synthesis context and therefore
|
||||
* should be as efficient as possible and not perform any operations considered
|
||||
* bad for realtime audio output (memory allocations and other OS calls).
|
||||
*/
|
||||
int (*notify)(fluid_preset_t* preset, int reason, int chan);
|
||||
};
|
||||
|
||||
|
||||
/*
|
||||
* fluid_sample_t
|
||||
/**
|
||||
* Virtual SoundFont sample.
|
||||
*/
|
||||
|
||||
struct _fluid_sample_t
|
||||
{
|
||||
char name[21];
|
||||
unsigned int start;
|
||||
unsigned int end; /* Note: Index of last valid sample point (contrary to SF spec) */
|
||||
unsigned int loopstart;
|
||||
unsigned int loopend; /* Note: first point following the loop (superimposed on loopstart) */
|
||||
unsigned int samplerate;
|
||||
int origpitch;
|
||||
int pitchadj;
|
||||
int sampletype;
|
||||
int valid;
|
||||
short* data;
|
||||
char name[21]; /**< Sample name */
|
||||
unsigned int start; /**< Start index */
|
||||
unsigned int end; /**< End index, index of last valid sample point (contrary to SF spec) */
|
||||
unsigned int loopstart; /**< Loop start index */
|
||||
unsigned int loopend; /**< Loop end index, first point following the loop (superimposed on loopstart) */
|
||||
unsigned int samplerate; /**< Sample rate */
|
||||
int origpitch; /**< Original pitch (MIDI note number, 0-127) */
|
||||
int pitchadj; /**< Fine pitch adjustment (+/- 99 cents) */
|
||||
int sampletype; /**< Values: #FLUID_SAMPLETYPE_MONO, FLUID_SAMPLETYPE_RIGHT, FLUID_SAMPLETYPE_LEFT, FLUID_SAMPLETYPE_ROM */
|
||||
int valid; /**< Should be TRUE if sample data is valid, FALSE otherwise (in which case it will not be synthesized) */
|
||||
short* data; /**< Pointer to the sample's data */
|
||||
|
||||
/** The amplitude, that will lower the level of the sample's loop to
|
||||
the noise floor. Needed for note turnoff optimization, will be
|
||||
filled out automatically */
|
||||
/* Set this to zero, when submitting a new sample. */
|
||||
int amplitude_that_reaches_noise_floor_is_valid;
|
||||
double amplitude_that_reaches_noise_floor;
|
||||
int amplitude_that_reaches_noise_floor_is_valid; /**< Indicates if \a amplitude_that_reaches_noise_floor is valid (TRUE), set to FALSE initially to calculate. */
|
||||
double amplitude_that_reaches_noise_floor; /**< The amplitude at which the sample's loop will be below the noise floor. For voice off optimization, calculated automatically. */
|
||||
|
||||
/** Count the number of playing voices that use this sample. */
|
||||
unsigned int refcount;
|
||||
unsigned int refcount; /**< Count of voices using this sample (use #fluid_sample_refcount to access this field) */
|
||||
|
||||
/** Implement this function if the sample or SoundFont needs to be
|
||||
notified when the sample is no longer used. */
|
||||
/**
|
||||
* Implement this function to receive notification when sample is no longer used.
|
||||
* @param sample Virtual SoundFont sample
|
||||
* @param reason #FLUID_SAMPLE_DONE only currently
|
||||
* @return Should return #FLUID_OK
|
||||
*/
|
||||
int (*notify)(fluid_sample_t* sample, int reason);
|
||||
|
||||
/** Pointer to SoundFont specific data */
|
||||
void* userdata;
|
||||
void* userdata; /**< User defined data */
|
||||
};
|
||||
|
||||
|
||||
#define fluid_sample_refcount(_sample) ((_sample)->refcount)
|
||||
#define fluid_sample_refcount(_sample) ((_sample)->refcount) /**< Get the reference count of a sample. Should only be called from within synthesis context (noteon method for example) */
|
||||
|
||||
|
||||
/** Sample types */
|
||||
|
||||
#define FLUID_SAMPLETYPE_MONO 1
|
||||
#define FLUID_SAMPLETYPE_RIGHT 2
|
||||
#define FLUID_SAMPLETYPE_LEFT 4
|
||||
#define FLUID_SAMPLETYPE_LINKED 8
|
||||
#define FLUID_SAMPLETYPE_ROM 0x8000
|
||||
#define FLUID_SAMPLETYPE_MONO 1 /**< Flag for #fluid_sample_t \a sampletype field for mono samples */
|
||||
#define FLUID_SAMPLETYPE_RIGHT 2 /**< Flag for #fluid_sample_t \a sampletype field for right samples of a stereo pair */
|
||||
#define FLUID_SAMPLETYPE_LEFT 4 /**< Flag for #fluid_sample_t \a sampletype field for left samples of a stereo pair */
|
||||
#define FLUID_SAMPLETYPE_LINKED 8 /**< Flag for #fluid_sample_t \a sampletype field, not used currently */
|
||||
#define FLUID_SAMPLETYPE_ROM 0x8000 /**< Flag for #fluid_sample_t \a sampletype field, ROM sample, causes sample to be ignored */
|
||||
|
||||
|
||||
|
||||
|
|
|
@ -27,17 +27,13 @@ extern "C" {
|
|||
#endif
|
||||
|
||||
|
||||
/*
|
||||
/**
|
||||
* @file shell.h
|
||||
* @brief Command shell interface
|
||||
*
|
||||
* Shell interface
|
||||
*
|
||||
* The shell interface allows you to send simple textual commands to
|
||||
* the synthesizer, to parse a command file, or to read commands
|
||||
* from the stdin or other input streams.
|
||||
*
|
||||
* To find the list of currently supported commands, please check the
|
||||
* fluid_cmd.c file.
|
||||
*
|
||||
* The shell interface allows you to send simple textual commands to
|
||||
* the synthesizer, to parse a command file, or to read commands
|
||||
* from the stdin or other input streams.
|
||||
*/
|
||||
|
||||
FLUIDSYNTH_API fluid_istream_t fluid_get_stdin(void);
|
||||
|
@ -47,29 +43,22 @@ FLUIDSYNTH_API char* fluid_get_userconf(char* buf, int len);
|
|||
FLUIDSYNTH_API char* fluid_get_sysconf(char* buf, int len);
|
||||
|
||||
|
||||
/** The command structure */
|
||||
|
||||
typedef int (*fluid_cmd_func_t)(void* data, int ac, char** av, fluid_ostream_t out);
|
||||
|
||||
/**
|
||||
* Shell command information structure.
|
||||
*/
|
||||
typedef struct {
|
||||
char* name; /** The name of the command, as typed in in the shell */
|
||||
char* topic; /** The help topic group of this command */
|
||||
fluid_cmd_func_t handler; /** Pointer to the handler for this command */
|
||||
void* data; /** Pointer to the user data */
|
||||
char* help; /** A help string */
|
||||
char* name; /**< The name of the command, as typed in the shell */
|
||||
char* topic; /**< The help topic group of this command */
|
||||
fluid_cmd_func_t handler; /**< Pointer to the handler for this command */
|
||||
void* data; /**< User data passed to the handler */
|
||||
char* help; /**< A help string */
|
||||
} fluid_cmd_t;
|
||||
|
||||
|
||||
/** The command handler */
|
||||
/* The command handler */
|
||||
|
||||
/**
|
||||
Create a new command handler. If the synth object passed as
|
||||
argument is not NULL, the handler will add all the default
|
||||
synthesizer commands to the command list.
|
||||
|
||||
\param synth The synthesizer object
|
||||
\returns A new command handler
|
||||
*/
|
||||
FLUIDSYNTH_API
|
||||
fluid_cmd_handler_t* new_fluid_cmd_handler(fluid_synth_t* synth);
|
||||
|
||||
|
@ -79,14 +68,6 @@ void delete_fluid_cmd_handler(fluid_cmd_handler_t* handler);
|
|||
FLUIDSYNTH_API
|
||||
void fluid_cmd_handler_set_synth(fluid_cmd_handler_t* handler, fluid_synth_t* synth);
|
||||
|
||||
/**
|
||||
Register a new command to the handler. The handler makes a private
|
||||
copy of the 'cmd' structure passed as argument.
|
||||
|
||||
\param handler A pointer to the command handler
|
||||
\param cmd A pointer to the command structure
|
||||
\returns 0 if the command was inserted, non-zero if error
|
||||
*/
|
||||
FLUIDSYNTH_API
|
||||
int fluid_cmd_handler_register(fluid_cmd_handler_t* handler, fluid_cmd_t* cmd);
|
||||
|
||||
|
@ -94,7 +75,7 @@ FLUIDSYNTH_API
|
|||
int fluid_cmd_handler_unregister(fluid_cmd_handler_t* handler, char* cmd);
|
||||
|
||||
|
||||
/** Command function */
|
||||
/* Command function */
|
||||
|
||||
FLUIDSYNTH_API
|
||||
int fluid_command(fluid_cmd_handler_t* handler, char* cmd, fluid_ostream_t out);
|
||||
|
@ -106,7 +87,7 @@ FLUIDSYNTH_API
|
|||
void fluid_usershell(fluid_settings_t* settings, fluid_cmd_handler_t* handler);
|
||||
|
||||
|
||||
/** Shell */
|
||||
/* Shell */
|
||||
|
||||
FLUIDSYNTH_API
|
||||
fluid_shell_t* new_fluid_shell(fluid_settings_t* settings, fluid_cmd_handler_t* handler,
|
||||
|
@ -116,8 +97,14 @@ FLUIDSYNTH_API void delete_fluid_shell(fluid_shell_t* shell);
|
|||
|
||||
|
||||
|
||||
/** TCP/IP server */
|
||||
/* TCP/IP server */
|
||||
|
||||
/**
|
||||
* Callback function which is executed for new server connections.
|
||||
* @param data User defined data supplied in call to new_fluid_server()
|
||||
* @param addr The IP address of the client (can be NULL)
|
||||
* @return Should return a new command handler for the connection (new_fluid_cmd_handler()).
|
||||
*/
|
||||
typedef fluid_cmd_handler_t* (*fluid_server_newclient_func_t)(void* data, char* addr);
|
||||
|
||||
FLUIDSYNTH_API
|
||||
|
|
|
@ -28,7 +28,8 @@ extern "C" {
|
|||
|
||||
|
||||
/**
|
||||
* Embedded synthesizer
|
||||
* @file synth.h
|
||||
* @brief Embeddable SoundFont synthesizer
|
||||
*
|
||||
* You create a new synthesizer with new_fluid_synth() and you destroy
|
||||
* if with delete_fluid_synth(). Use the settings structure to specify
|
||||
|
@ -109,11 +110,10 @@ FLUIDSYNTH_API double fluid_synth_get_reverb_damp(fluid_synth_t* synth);
|
|||
FLUIDSYNTH_API double fluid_synth_get_reverb_level(fluid_synth_t* synth);
|
||||
FLUIDSYNTH_API double fluid_synth_get_reverb_width(fluid_synth_t* synth);
|
||||
|
||||
/* Default settings for the reverb */
|
||||
#define FLUID_REVERB_DEFAULT_ROOMSIZE 0.2f
|
||||
#define FLUID_REVERB_DEFAULT_DAMP 0.0f
|
||||
#define FLUID_REVERB_DEFAULT_WIDTH 0.5f
|
||||
#define FLUID_REVERB_DEFAULT_LEVEL 0.9f
|
||||
#define FLUID_REVERB_DEFAULT_ROOMSIZE 0.2f /**< Default reverb room size */
|
||||
#define FLUID_REVERB_DEFAULT_DAMP 0.0f /**< Default reverb damping */
|
||||
#define FLUID_REVERB_DEFAULT_WIDTH 0.5f /**< Default reverb width */
|
||||
#define FLUID_REVERB_DEFAULT_LEVEL 0.9f /**< Default reverb level */
|
||||
|
||||
|
||||
/* Chorus */
|
||||
|
@ -135,12 +135,11 @@ FLUIDSYNTH_API double fluid_synth_get_chorus_speed_Hz(fluid_synth_t* synth);
|
|||
FLUIDSYNTH_API double fluid_synth_get_chorus_depth_ms(fluid_synth_t* synth);
|
||||
FLUIDSYNTH_API int fluid_synth_get_chorus_type(fluid_synth_t* synth); /* see fluid_chorus_mod */
|
||||
|
||||
/* Default settings for the chorus. */
|
||||
#define FLUID_CHORUS_DEFAULT_N 3
|
||||
#define FLUID_CHORUS_DEFAULT_LEVEL 2.0f
|
||||
#define FLUID_CHORUS_DEFAULT_SPEED 0.3f
|
||||
#define FLUID_CHORUS_DEFAULT_DEPTH 8.0f
|
||||
#define FLUID_CHORUS_DEFAULT_TYPE FLUID_CHORUS_MOD_SINE
|
||||
#define FLUID_CHORUS_DEFAULT_N 3 /**< Default chorus voice count */
|
||||
#define FLUID_CHORUS_DEFAULT_LEVEL 2.0f /**< Default chorus level */
|
||||
#define FLUID_CHORUS_DEFAULT_SPEED 0.3f /**< Default chorus speed */
|
||||
#define FLUID_CHORUS_DEFAULT_DEPTH 8.0f /**< Default chorus depth */
|
||||
#define FLUID_CHORUS_DEFAULT_TYPE FLUID_CHORUS_MOD_SINE /**< Default chorus waveform type */
|
||||
|
||||
|
||||
/* Audio and MIDI channels */
|
||||
|
@ -172,11 +171,8 @@ enum fluid_interp {
|
|||
FLUID_INTERP_7THORDER = 7, /**< Seventh-order interpolation */
|
||||
};
|
||||
|
||||
/** Default interpolation method from #fluid_interp. */
|
||||
#define FLUID_INTERP_DEFAULT FLUID_INTERP_4THORDER
|
||||
|
||||
/** Highest interpolation method from #fluid_interp. */
|
||||
#define FLUID_INTERP_HIGHEST FLUID_INTERP_7THORDER
|
||||
#define FLUID_INTERP_DEFAULT FLUID_INTERP_4THORDER /**< Default interpolation method from #fluid_interp. */
|
||||
#define FLUID_INTERP_HIGHEST FLUID_INTERP_7THORDER /**< Highest interpolation method from #fluid_interp. */
|
||||
|
||||
|
||||
/* Generator interface */
|
||||
|
|
|
@ -28,36 +28,36 @@ extern "C" {
|
|||
#endif
|
||||
|
||||
|
||||
/*
|
||||
/**
|
||||
* @file types.h
|
||||
* @brief Type declarations
|
||||
*/
|
||||
|
||||
Forward declarations
|
||||
typedef struct _fluid_hashtable_t fluid_settings_t; /**< Configuration settings instance */
|
||||
typedef struct _fluid_synth_t fluid_synth_t; /**< Synthesizer instance */
|
||||
typedef struct _fluid_voice_t fluid_voice_t; /**< Synthesis voice instance */
|
||||
typedef struct _fluid_sfloader_t fluid_sfloader_t; /**< SoundFont loader plugin */
|
||||
typedef struct _fluid_sfont_t fluid_sfont_t; /**< SoundFont */
|
||||
typedef struct _fluid_preset_t fluid_preset_t; /**< SoundFont preset */
|
||||
typedef struct _fluid_sample_t fluid_sample_t; /**< SoundFont sample */
|
||||
typedef struct _fluid_mod_t fluid_mod_t; /**< SoundFont modulator */
|
||||
typedef struct _fluid_audio_driver_t fluid_audio_driver_t; /**< Audio driver instance */
|
||||
typedef struct _fluid_file_renderer_t fluid_file_renderer_t; /**< Audio file renderer instance */
|
||||
typedef struct _fluid_player_t fluid_player_t; /**< MIDI player instance */
|
||||
typedef struct _fluid_midi_event_t fluid_midi_event_t; /**< MIDI event */
|
||||
typedef struct _fluid_midi_driver_t fluid_midi_driver_t; /**< MIDI driver instance */
|
||||
typedef struct _fluid_midi_router_t fluid_midi_router_t; /**< MIDI router instance */
|
||||
typedef struct _fluid_midi_router_rule_t fluid_midi_router_rule_t; /**< MIDI router rule */
|
||||
typedef struct _fluid_hashtable_t fluid_cmd_handler_t; /**< Command handler */
|
||||
typedef struct _fluid_shell_t fluid_shell_t; /**< Command shell */
|
||||
typedef struct _fluid_server_t fluid_server_t; /**< TCP/IP shell server instance */
|
||||
typedef struct _fluid_event_t fluid_event_t; /**< Sequencer event */
|
||||
typedef struct _fluid_sequencer_t fluid_sequencer_t; /**< Sequencer instance */
|
||||
typedef struct _fluid_ramsfont_t fluid_ramsfont_t; /**< RAM SoundFont */
|
||||
typedef struct _fluid_rampreset_t fluid_rampreset_t; /**< RAM SoundFont preset */
|
||||
|
||||
*/
|
||||
typedef struct _fluid_hashtable_t fluid_settings_t;
|
||||
typedef struct _fluid_synth_t fluid_synth_t;
|
||||
typedef struct _fluid_voice_t fluid_voice_t;
|
||||
typedef struct _fluid_sfloader_t fluid_sfloader_t;
|
||||
typedef struct _fluid_sfont_t fluid_sfont_t;
|
||||
typedef struct _fluid_preset_t fluid_preset_t;
|
||||
typedef struct _fluid_sample_t fluid_sample_t;
|
||||
typedef struct _fluid_mod_t fluid_mod_t;
|
||||
typedef struct _fluid_audio_driver_t fluid_audio_driver_t;
|
||||
typedef struct _fluid_file_renderer_t fluid_file_renderer_t;
|
||||
typedef struct _fluid_player_t fluid_player_t;
|
||||
typedef struct _fluid_midi_event_t fluid_midi_event_t;
|
||||
typedef struct _fluid_midi_driver_t fluid_midi_driver_t;
|
||||
typedef struct _fluid_midi_router_t fluid_midi_router_t;
|
||||
typedef struct _fluid_midi_router_rule_t fluid_midi_router_rule_t;
|
||||
typedef struct _fluid_hashtable_t fluid_cmd_handler_t;
|
||||
typedef struct _fluid_shell_t fluid_shell_t;
|
||||
typedef struct _fluid_server_t fluid_server_t;
|
||||
typedef struct _fluid_event_t fluid_event_t;
|
||||
typedef struct _fluid_sequencer_t fluid_sequencer_t;
|
||||
typedef struct _fluid_ramsfont_t fluid_ramsfont_t;
|
||||
typedef struct _fluid_rampreset_t fluid_rampreset_t;
|
||||
|
||||
typedef int fluid_istream_t;
|
||||
typedef int fluid_ostream_t;
|
||||
typedef int fluid_istream_t; /**< Input stream descriptor */
|
||||
typedef int fluid_ostream_t; /**< Output stream descriptor */
|
||||
|
||||
|
||||
#ifdef __cplusplus
|
||||
|
|
|
@ -26,14 +26,17 @@
|
|||
extern "C" {
|
||||
#endif
|
||||
|
||||
#define FLUIDSYNTH_VERSION @FLUIDSYNTH_VERSION@
|
||||
#define FLUIDSYNTH_VERSION_MAJOR @FLUIDSYNTH_VERSION_MAJOR@
|
||||
#define FLUIDSYNTH_VERSION_MINOR @FLUIDSYNTH_VERSION_MINOR@
|
||||
#define FLUIDSYNTH_VERSION_MICRO @FLUIDSYNTH_VERSION_MICRO@
|
||||
/**
|
||||
* @file version.h
|
||||
* @brief Library version functions and defines
|
||||
*/
|
||||
|
||||
#define FLUIDSYNTH_VERSION @FLUIDSYNTH_VERSION@ /**< String constant of libfluidsynth version. */
|
||||
#define FLUIDSYNTH_VERSION_MAJOR @FLUIDSYNTH_VERSION_MAJOR@ /**< libfluidsynth major version integer constant. */
|
||||
#define FLUIDSYNTH_VERSION_MINOR @FLUIDSYNTH_VERSION_MINOR@ /**< libfluidsynth minor version integer constant. */
|
||||
#define FLUIDSYNTH_VERSION_MICRO @FLUIDSYNTH_VERSION_MICRO@ /**< libfluidsynth micro version integer constant. */
|
||||
|
||||
FLUIDSYNTH_API void fluid_version(int *major, int *minor, int *micro);
|
||||
|
||||
FLUIDSYNTH_API char* fluid_version_str(void);
|
||||
|
||||
|
||||
|
|
|
@ -25,69 +25,36 @@
|
|||
extern "C" {
|
||||
#endif
|
||||
|
||||
/**
|
||||
* @file voice.h
|
||||
* @brief Synthesis voice manipulation functions.
|
||||
*
|
||||
* The interface to the synthesizer's voices.
|
||||
* Examples on using them can be found in fluid_defsfont.c.
|
||||
* Most of these functions should only be called from within synthesis context,
|
||||
* such as the SoundFont loader's noteon method.
|
||||
*/
|
||||
|
||||
/*
|
||||
* The interface to the synthesizer's voices
|
||||
* Examples on using them can be found in fluid_defsfont.c
|
||||
*/
|
||||
|
||||
/** Update all the synthesis parameters, which depend on generator gen.
|
||||
This is only necessary after changing a generator of an already operating voice.
|
||||
Most applications will not need this function.*/
|
||||
|
||||
FLUIDSYNTH_API void fluid_voice_update_param(fluid_voice_t* voice, int gen);
|
||||
|
||||
|
||||
/* for fluid_voice_add_mod */
|
||||
enum fluid_voice_add_mod{
|
||||
FLUID_VOICE_OVERWRITE,
|
||||
FLUID_VOICE_ADD,
|
||||
FLUID_VOICE_DEFAULT
|
||||
/**
|
||||
* Enum used with fluid_voice_add_mod() to specify how to handle duplicate modulators.
|
||||
*/
|
||||
enum fluid_voice_add_mod {
|
||||
FLUID_VOICE_OVERWRITE, /**< Overwrite any existing matching modulator */
|
||||
FLUID_VOICE_ADD, /**< Add (sum) modulator amounts */
|
||||
FLUID_VOICE_DEFAULT /**< For default modulators only, no need to check for duplicates */
|
||||
};
|
||||
|
||||
/* Add a modulator to a voice (SF2.1 only). */
|
||||
FLUIDSYNTH_API void fluid_voice_add_mod(fluid_voice_t* voice, fluid_mod_t* mod, int mode);
|
||||
|
||||
/** Set the value of a generator */
|
||||
FLUIDSYNTH_API void fluid_voice_gen_set(fluid_voice_t* voice, int gen, float val);
|
||||
|
||||
/** Get the value of a generator */
|
||||
FLUIDSYNTH_API float fluid_voice_gen_get(fluid_voice_t* voice, int gen);
|
||||
|
||||
/** Modify the value of a generator by val */
|
||||
FLUIDSYNTH_API void fluid_voice_gen_incr(fluid_voice_t* voice, int gen, float val);
|
||||
|
||||
|
||||
/** Return the unique ID of the noteon-event. A sound font loader
|
||||
* may store the voice processes it has created for * real-time
|
||||
* control during the operation of a voice (for example: parameter
|
||||
* changes in sound font editor). The synth uses a pool of
|
||||
* voices, which are 'recycled' and never deallocated.
|
||||
*
|
||||
* Before modifying an existing voice, check
|
||||
* - that its state is still 'playing'
|
||||
* - that the ID is still the same
|
||||
* Otherwise the voice has finished playing.
|
||||
*/
|
||||
FLUIDSYNTH_API unsigned int fluid_voice_get_id(fluid_voice_t* voice);
|
||||
|
||||
|
||||
FLUIDSYNTH_API int fluid_voice_is_playing(fluid_voice_t* voice);
|
||||
|
||||
/** If the peak volume during the loop is known, then the voice can
|
||||
* be released earlier during the release phase. Otherwise, the
|
||||
* voice will operate (inaudibly), until the envelope is at the
|
||||
* nominal turnoff point. In many cases the loop volume is many dB
|
||||
* below the maximum volume. For example, the loop volume for a
|
||||
* typical acoustic piano is 20 dB below max. Taking that into
|
||||
* account in the turn-off algorithm we can save 20 dB / 100 dB =>
|
||||
* 1/5 of the total release time.
|
||||
* So it's a good idea to call fluid_voice_optimize_sample
|
||||
* on each sample once.
|
||||
*/
|
||||
|
||||
FLUIDSYNTH_API int fluid_voice_optimize_sample(fluid_sample_t* s);
|
||||
|
||||
FLUIDSYNTH_API int fluid_voice_optimize_sample(fluid_sample_t* s);
|
||||
|
||||
|
||||
#ifdef __cplusplus
|
||||
|
|
|
@ -368,6 +368,7 @@ new_fluid_audio_driver(fluid_settings_t* settings, fluid_synth_t* synth)
|
|||
* Like new_fluid_audio_driver() but allows for custom audio processing before
|
||||
* audio is sent to audio driver. It is the responsibility of the callback
|
||||
* 'func' to render the audio into the buffers.
|
||||
*
|
||||
* NOTE: Not as efficient as new_fluid_audio_driver().
|
||||
*/
|
||||
fluid_audio_driver_t*
|
||||
|
|
|
@ -36,6 +36,19 @@
|
|||
#define MAX_COMMAND_LEN 1024 /* max command length accepted by fluid_command() */
|
||||
#define FLUID_WORKLINELENGTH 1024 /* LADSPA plugins use long command lines */
|
||||
|
||||
struct _fluid_shell_t {
|
||||
fluid_settings_t* settings;
|
||||
fluid_cmd_handler_t* handler;
|
||||
fluid_thread_t* thread;
|
||||
fluid_istream_t in;
|
||||
fluid_ostream_t out;
|
||||
};
|
||||
|
||||
static int fluid_shell_run(fluid_shell_t* shell);
|
||||
static void fluid_shell_init(fluid_shell_t* shell,
|
||||
fluid_settings_t* settings, fluid_cmd_handler_t* handler,
|
||||
fluid_istream_t in, fluid_ostream_t out);
|
||||
|
||||
void fluid_shell_settings(fluid_settings_t* settings)
|
||||
{
|
||||
fluid_settings_register_str(settings, "shell.prompt", "", 0, NULL, NULL);
|
||||
|
@ -157,8 +170,8 @@ fluid_cmd_t fluid_commands[] = {
|
|||
|
||||
/**
|
||||
* Process a string command.
|
||||
* NOTE: FluidSynth 1.0.8+ no longer modifies the 'cmd' string.
|
||||
* @param handle FluidSynth command handler
|
||||
* NOTE: FluidSynth 1.0.8 and above no longer modifies the 'cmd' string.
|
||||
* @param handler FluidSynth command handler
|
||||
* @param cmd Command string (NOTE: Gets modified by FluidSynth prior to 1.0.8)
|
||||
* @param out Output stream to display command response to
|
||||
* @return Integer value corresponding to: -1 on command error, 0 on success,
|
||||
|
@ -196,20 +209,6 @@ fluid_command(fluid_cmd_handler_t* handler, char* cmd, fluid_ostream_t out)
|
|||
return fluid_cmd_handler_handle(handler, num_tokens, &token[0], out);
|
||||
}
|
||||
|
||||
struct _fluid_shell_t {
|
||||
fluid_settings_t* settings;
|
||||
fluid_cmd_handler_t* handler;
|
||||
fluid_thread_t* thread;
|
||||
fluid_istream_t in;
|
||||
fluid_ostream_t out;
|
||||
};
|
||||
|
||||
int fluid_shell_run(fluid_shell_t* shell);
|
||||
void fluid_shell_init(fluid_shell_t* shell,
|
||||
fluid_settings_t* settings, fluid_cmd_handler_t* handler,
|
||||
fluid_istream_t in, fluid_ostream_t out);
|
||||
|
||||
|
||||
/**
|
||||
* Create a new FluidSynth command shell.
|
||||
* @param settings Setting parameters to use with the shell
|
||||
|
@ -246,12 +245,12 @@ new_fluid_shell(fluid_settings_t* settings, fluid_cmd_handler_t* handler,
|
|||
}
|
||||
|
||||
return shell;
|
||||
|
||||
}
|
||||
|
||||
void fluid_shell_init(fluid_shell_t* shell,
|
||||
fluid_settings_t* settings, fluid_cmd_handler_t* handler,
|
||||
fluid_istream_t in, fluid_ostream_t out)
|
||||
static void
|
||||
fluid_shell_init(fluid_shell_t* shell,
|
||||
fluid_settings_t* settings, fluid_cmd_handler_t* handler,
|
||||
fluid_istream_t in, fluid_ostream_t out)
|
||||
{
|
||||
shell->settings = settings;
|
||||
shell->handler = handler;
|
||||
|
@ -259,7 +258,12 @@ void fluid_shell_init(fluid_shell_t* shell,
|
|||
shell->out = out;
|
||||
}
|
||||
|
||||
void delete_fluid_shell(fluid_shell_t* shell)
|
||||
/**
|
||||
* Delete a FluidSynth command shell.
|
||||
* @param shell Command shell instance
|
||||
*/
|
||||
void
|
||||
delete_fluid_shell(fluid_shell_t* shell)
|
||||
{
|
||||
if (shell->thread != NULL) {
|
||||
delete_fluid_thread(shell->thread);
|
||||
|
@ -268,8 +272,8 @@ void delete_fluid_shell(fluid_shell_t* shell)
|
|||
FLUID_FREE(shell);
|
||||
}
|
||||
|
||||
|
||||
int fluid_shell_run(fluid_shell_t* shell)
|
||||
static int
|
||||
fluid_shell_run(fluid_shell_t* shell)
|
||||
{
|
||||
char workline[FLUID_WORKLINELENGTH];
|
||||
char* prompt = NULL;
|
||||
|
@ -321,7 +325,12 @@ int fluid_shell_run(fluid_shell_t* shell)
|
|||
return errors;
|
||||
}
|
||||
|
||||
|
||||
/**
|
||||
* A convenience function to create a shell interfacing to standard input/output
|
||||
* console streams.
|
||||
* @param settings Settings instance for the shell
|
||||
* @param handler Command handler callback
|
||||
*/
|
||||
void
|
||||
fluid_usershell(fluid_settings_t* settings, fluid_cmd_handler_t* handler)
|
||||
{
|
||||
|
@ -330,6 +339,12 @@ fluid_usershell(fluid_settings_t* settings, fluid_cmd_handler_t* handler)
|
|||
fluid_shell_run(&shell);
|
||||
}
|
||||
|
||||
/**
|
||||
* Execute shell commands in a file.
|
||||
* @param handler Command handler callback
|
||||
* @param filename File name
|
||||
* @return 0 on success, a value >1 on error
|
||||
*/
|
||||
int
|
||||
fluid_source(fluid_cmd_handler_t* handler, char* filename)
|
||||
{
|
||||
|
@ -348,7 +363,12 @@ fluid_source(fluid_cmd_handler_t* handler, char* filename)
|
|||
return fluid_shell_run(&shell);
|
||||
}
|
||||
|
||||
|
||||
/**
|
||||
* Get the user specific FluidSynth command file name.
|
||||
* @param buf Caller supplied string buffer to store file name to.
|
||||
* @param len Length of \a buf
|
||||
* @return Returns \a buf pointer or NULL if no user command file for this system type.
|
||||
*/
|
||||
char*
|
||||
fluid_get_userconf(char* buf, int len)
|
||||
{
|
||||
|
@ -365,6 +385,12 @@ fluid_get_userconf(char* buf, int len)
|
|||
#endif
|
||||
}
|
||||
|
||||
/**
|
||||
* Get the system FluidSynth command file name.
|
||||
* @param buf Caller supplied string buffer to store file name to.
|
||||
* @param len Length of \a buf
|
||||
* @return Returns \a buf pointer or NULL if no system command file for this system type.
|
||||
*/
|
||||
char*
|
||||
fluid_get_sysconf(char* buf, int len)
|
||||
{
|
||||
|
@ -1589,7 +1615,14 @@ fluid_cmd_handler_destroy_hash_value (void *value)
|
|||
delete_fluid_cmd ((fluid_cmd_t *)value);
|
||||
}
|
||||
|
||||
fluid_cmd_handler_t* new_fluid_cmd_handler(fluid_synth_t* synth)
|
||||
/**
|
||||
* Create a new command handler.
|
||||
* @param synth If not NULL, all the default synthesizer commands will be
|
||||
* added to the new handler.
|
||||
* @return New command handler
|
||||
*/
|
||||
fluid_cmd_handler_t *
|
||||
new_fluid_cmd_handler(fluid_synth_t* synth)
|
||||
{
|
||||
int i;
|
||||
fluid_cmd_handler_t* handler;
|
||||
|
@ -1619,24 +1652,44 @@ fluid_cmd_handler_t* new_fluid_cmd_handler(fluid_synth_t* synth)
|
|||
return handler;
|
||||
}
|
||||
|
||||
void delete_fluid_cmd_handler(fluid_cmd_handler_t* handler)
|
||||
/**
|
||||
* Delete a command handler.
|
||||
* @param handler Command handler to delete
|
||||
*/
|
||||
void
|
||||
delete_fluid_cmd_handler(fluid_cmd_handler_t* handler)
|
||||
{
|
||||
delete_fluid_hashtable (handler);
|
||||
}
|
||||
|
||||
int fluid_cmd_handler_register(fluid_cmd_handler_t* handler, fluid_cmd_t* cmd)
|
||||
/**
|
||||
* Register a new command to the handler.
|
||||
* @param handler Command handler instance
|
||||
* @param cmd Command info (gets copied)
|
||||
* @return #FLUID_OK if command was inserted, #FLUID_FAILED otherwise
|
||||
*/
|
||||
int
|
||||
fluid_cmd_handler_register(fluid_cmd_handler_t* handler, fluid_cmd_t* cmd)
|
||||
{
|
||||
fluid_cmd_t* copy = fluid_cmd_copy(cmd);
|
||||
fluid_hashtable_insert(handler, copy->name, copy);
|
||||
return 0;
|
||||
return FLUID_OK;
|
||||
}
|
||||
|
||||
int fluid_cmd_handler_unregister(fluid_cmd_handler_t* handler, char* cmd)
|
||||
/**
|
||||
* Unregister a command from a command handler.
|
||||
* @param handler Command handler instance
|
||||
* @param cmd Name of the command
|
||||
* @return TRUE if command was found and unregistered, FALSE otherwise
|
||||
*/
|
||||
int
|
||||
fluid_cmd_handler_unregister(fluid_cmd_handler_t* handler, char* cmd)
|
||||
{
|
||||
return fluid_hashtable_remove(handler, cmd);
|
||||
}
|
||||
|
||||
int fluid_cmd_handler_handle(fluid_cmd_handler_t* handler, int ac, char** av, fluid_ostream_t out)
|
||||
int
|
||||
fluid_cmd_handler_handle(fluid_cmd_handler_t* handler, int ac, char** av, fluid_ostream_t out)
|
||||
{
|
||||
fluid_cmd_t* cmd;
|
||||
|
||||
|
@ -1668,6 +1721,13 @@ static void fluid_server_handle_connection(fluid_server_t* server,
|
|||
char* addr);
|
||||
static void fluid_server_close(fluid_server_t* server);
|
||||
|
||||
/**
|
||||
* Create a new TCP/IP command shell server.
|
||||
* @param settings Settings instance to use for the shell
|
||||
* @param newclient Callback function to call for each new client connection
|
||||
* @param data User defined data to pass to \a newclient callback
|
||||
* @return New shell server instance or NULL on error
|
||||
*/
|
||||
fluid_server_t*
|
||||
new_fluid_server(fluid_settings_t* settings,
|
||||
fluid_server_newclient_func_t newclient,
|
||||
|
@ -1702,7 +1762,12 @@ new_fluid_server(fluid_settings_t* settings,
|
|||
return server;
|
||||
}
|
||||
|
||||
void delete_fluid_server(fluid_server_t* server)
|
||||
/**
|
||||
* Delete a TCP/IP shell server.
|
||||
* @param server Shell server instance
|
||||
*/
|
||||
void
|
||||
delete_fluid_server(fluid_server_t* server)
|
||||
{
|
||||
if (server == NULL) {
|
||||
return;
|
||||
|
@ -1776,6 +1841,11 @@ void fluid_server_remove_client(fluid_server_t* server, fluid_client_t* client)
|
|||
fluid_mutex_unlock(server->mutex);
|
||||
}
|
||||
|
||||
/**
|
||||
* Join a shell server thread (wait until it quits).
|
||||
* @param server Shell server instance
|
||||
* @return #FLUID_OK on success, #FLUID_FAILED otherwise
|
||||
*/
|
||||
int fluid_server_join(fluid_server_t* server)
|
||||
{
|
||||
return fluid_server_socket_join(server->socket);
|
||||
|
|
|
@ -38,6 +38,12 @@ BOOL WINAPI DllMain(HANDLE hModule, DWORD ul_reason_for_call, LPVOID lpReserved)
|
|||
}
|
||||
#endif
|
||||
|
||||
/**
|
||||
* Set the handle to the instance of the application on the Windows platform.
|
||||
* @param Application instance pointer
|
||||
*
|
||||
* The handle is needed to open DirectSound.
|
||||
*/
|
||||
void fluid_set_hinstance(void* hinstance)
|
||||
{
|
||||
if (fluid_hinstance == NULL) {
|
||||
|
@ -46,6 +52,10 @@ void fluid_set_hinstance(void* hinstance)
|
|||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* Get the handle to the instance of the application on the Windows platform.
|
||||
* @return Application instance pointer or NULL if not set
|
||||
*/
|
||||
void* fluid_get_hinstance(void)
|
||||
{
|
||||
return (void*) fluid_hinstance;
|
||||
|
|
|
@ -124,18 +124,18 @@ typedef struct
|
|||
*/
|
||||
typedef struct
|
||||
{
|
||||
char type; /**< #fluid_event_queue_elem */
|
||||
char type; /**< fluid_event_queue_elem */
|
||||
|
||||
union
|
||||
{
|
||||
fluid_midi_event_t midi; /**< If type == #FLUID_EVENT_QUEUE_ELEM_MIDI */
|
||||
fluid_event_gen_t gen; /**< If type == #FLUID_EVENT_QUEUE_ELEM_GEN */
|
||||
fluid_event_preset_t preset; /**< If type == #FLUID_EVENT_QUEUE_ELEM_PRESET */
|
||||
fluid_event_reverb_t reverb; /**< If type == #FLUID_EVENT_QUEUE_ELEM_REVERB */
|
||||
fluid_event_chorus_t chorus; /**< If type == #FLUID_EVENT_QUEUE_ELEM_CHORUS */
|
||||
fluid_event_set_tuning_t set_tuning; /**< If type == #FLUID_EVENT_QUEUE_ELEM_SET_TUNING */
|
||||
fluid_event_repl_tuning_t repl_tuning; /**< If type == #FLUID_EVENT_QUEUE_ELEM_REPL_TUNING */
|
||||
fluid_event_unref_tuning_t unref_tuning; /**< If type == #FLUID_EVENT_QUEUE_ELEM_UNREF_TUNING */
|
||||
fluid_midi_event_t midi; /**< If type == FLUID_EVENT_QUEUE_ELEM_MIDI */
|
||||
fluid_event_gen_t gen; /**< If type == FLUID_EVENT_QUEUE_ELEM_GEN */
|
||||
fluid_event_preset_t preset; /**< If type == FLUID_EVENT_QUEUE_ELEM_PRESET */
|
||||
fluid_event_reverb_t reverb; /**< If type == FLUID_EVENT_QUEUE_ELEM_REVERB */
|
||||
fluid_event_chorus_t chorus; /**< If type == FLUID_EVENT_QUEUE_ELEM_CHORUS */
|
||||
fluid_event_set_tuning_t set_tuning; /**< If type == FLUID_EVENT_QUEUE_ELEM_SET_TUNING */
|
||||
fluid_event_repl_tuning_t repl_tuning; /**< If type == FLUID_EVENT_QUEUE_ELEM_REPL_TUNING */
|
||||
fluid_event_unref_tuning_t unref_tuning; /**< If type == FLUID_EVENT_QUEUE_ELEM_UNREF_TUNING */
|
||||
double dval; /**< A floating point payload value */
|
||||
int ival; /**< An integer payload value */
|
||||
void *pval; /**< A pointer payload value */
|
||||
|
|
|
@ -129,16 +129,20 @@ const char *endian_names[] = {
|
|||
* Create a new file renderer and open the file.
|
||||
* @param synth The synth that creates audio data.
|
||||
* @return the new object, or NULL on failure
|
||||
* @since: 1.1.0
|
||||
* @since 1.1.0
|
||||
*
|
||||
* NOTE: Uses the following settings from the synth object:
|
||||
* audio.file.name: Output filename
|
||||
* audio.file.type: File type, "auto" tries to determine type from filename
|
||||
* extension with fallback to "wav".
|
||||
* audio.file.format: Audio format
|
||||
* audio.file.endian: Endian byte order, "auto" for file type's default byte order
|
||||
* audio.period-size: Size of audio blocks to process
|
||||
* synth.sample-rate: Sample rate to use
|
||||
* NOTE: Available file types and formats depends on if libfluidsynth was
|
||||
* built with libsndfile support or not. If not then only RAW 16 bit output is
|
||||
* supported.
|
||||
*
|
||||
* Uses the following settings from the synth object:
|
||||
* - audio.file.name: Output filename
|
||||
* - audio.file.type: File type, "auto" tries to determine type from filename
|
||||
* extension with fallback to "wav".
|
||||
* - audio.file.format: Audio format
|
||||
* - audio.file.endian: Endian byte order, "auto" for file type's default byte order
|
||||
* - audio.period-size: Size of audio blocks to process
|
||||
* - synth.sample-rate: Sample rate to use
|
||||
*/
|
||||
fluid_file_renderer_t *
|
||||
new_fluid_file_renderer(fluid_synth_t* synth)
|
||||
|
@ -241,7 +245,7 @@ new_fluid_file_renderer(fluid_synth_t* synth)
|
|||
/**
|
||||
* Close file and destroy a file renderer object.
|
||||
* @param dev File renderer object.
|
||||
* @since: 1.1.0
|
||||
* @since 1.1.0
|
||||
*/
|
||||
void delete_fluid_file_renderer(fluid_file_renderer_t* dev)
|
||||
{
|
||||
|
@ -274,7 +278,7 @@ void delete_fluid_file_renderer(fluid_file_renderer_t* dev)
|
|||
* Write period_size samples to file.
|
||||
* @param dev File renderer instance
|
||||
* @return FLUID_OK or FLUID_FAILED if an error occurred
|
||||
* @since: 1.1.0
|
||||
* @since 1.1.0
|
||||
*/
|
||||
int
|
||||
fluid_file_renderer_process_block(fluid_file_renderer_t* dev)
|
||||
|
|
|
@ -35,7 +35,7 @@ extern lash_client_t * fluid_lash_client;
|
|||
#define fluid_lash_alsa_client_id lash_alsa_client_id
|
||||
#define fluid_lash_jack_client_name lash_jack_client_name
|
||||
|
||||
#else /* old depricated LADCCA support which will be removed someday */
|
||||
#else /* old deprecated LADCCA support which will be removed someday */
|
||||
|
||||
#include <ladcca/ladcca.h>
|
||||
extern cca_client_t * fluid_lash_client;
|
||||
|
|
|
@ -198,11 +198,11 @@ void fluid_midi_driver_settings(fluid_settings_t* settings)
|
|||
|
||||
|
||||
/**
|
||||
* Write a list of midi driver names into a buffer.
|
||||
* Write a list of MIDI driver names into a buffer.
|
||||
* (A buffer length of 256 characters should be more than enough.)
|
||||
* @param buf buffert to write names into
|
||||
* @param buflen maximum amount of characters in buf.
|
||||
* @param separator separator string, written between names.
|
||||
* @param buf Buffer to write names into
|
||||
* @param buflen Maximum amount of characters in buf.
|
||||
* @param separator Separator string, written between names.
|
||||
* @since 1.1.0
|
||||
*/
|
||||
void
|
||||
|
|
|
@ -676,7 +676,7 @@ fluid_midi_event_t* new_fluid_midi_event()
|
|||
/**
|
||||
* Delete MIDI event structure.
|
||||
* @param evt MIDI event structure
|
||||
* @return Always returns 0
|
||||
* @return Always returns #FLUID_OK
|
||||
*/
|
||||
int delete_fluid_midi_event(fluid_midi_event_t* evt)
|
||||
{
|
||||
|
@ -686,7 +686,7 @@ int delete_fluid_midi_event(fluid_midi_event_t* evt)
|
|||
{
|
||||
temp = evt->next;
|
||||
|
||||
/* Dynamic SYSEX event? - free (param2 indicates if dynamic) */
|
||||
/* Dynamic SYSEX event? - free (param2 indicates if dynamic) */
|
||||
if (evt->type == MIDI_SYSEX && evt->paramptr && evt->param2)
|
||||
FLUID_FREE (evt->paramptr);
|
||||
|
||||
|
@ -698,9 +698,8 @@ int delete_fluid_midi_event(fluid_midi_event_t* evt)
|
|||
|
||||
/**
|
||||
* Get the event type field of a MIDI event structure.
|
||||
* DOCME - Event type enum appears to be internal (fluid_midi.h)
|
||||
* @param evt MIDI event structure
|
||||
* @return Event type field
|
||||
* @return Event type field (MIDI status byte without channel)
|
||||
*/
|
||||
int fluid_midi_event_get_type(fluid_midi_event_t* evt)
|
||||
{
|
||||
|
@ -709,10 +708,9 @@ int fluid_midi_event_get_type(fluid_midi_event_t* evt)
|
|||
|
||||
/**
|
||||
* Set the event type field of a MIDI event structure.
|
||||
* DOCME - Event type enum appears to be internal (fluid_midi.h)
|
||||
* @param evt MIDI event structure
|
||||
* @param type Event type field
|
||||
* @return Always returns 0
|
||||
* @param type Event type field (MIDI status byte without channel)
|
||||
* @return Always returns #FLUID_OK
|
||||
*/
|
||||
int fluid_midi_event_set_type(fluid_midi_event_t* evt, int type)
|
||||
{
|
||||
|
@ -734,7 +732,7 @@ int fluid_midi_event_get_channel(fluid_midi_event_t* evt)
|
|||
* Set the channel field of a MIDI event structure.
|
||||
* @param evt MIDI event structure
|
||||
* @param chan MIDI channel field
|
||||
* @return Always returns 0
|
||||
* @return Always returns #FLUID_OK
|
||||
*/
|
||||
int fluid_midi_event_set_channel(fluid_midi_event_t* evt, int chan)
|
||||
{
|
||||
|
@ -756,7 +754,7 @@ int fluid_midi_event_get_key(fluid_midi_event_t* evt)
|
|||
* Set the key field of a MIDI event structure.
|
||||
* @param evt MIDI event structure
|
||||
* @param v MIDI note number (0-127)
|
||||
* @return Always returns 0
|
||||
* @return Always returns #FLUID_OK
|
||||
*/
|
||||
int fluid_midi_event_set_key(fluid_midi_event_t* evt, int v)
|
||||
{
|
||||
|
@ -778,7 +776,7 @@ int fluid_midi_event_get_velocity(fluid_midi_event_t* evt)
|
|||
* Set the velocity field of a MIDI event structure.
|
||||
* @param evt MIDI event structure
|
||||
* @param v MIDI velocity value
|
||||
* @return Always returns 0
|
||||
* @return Always returns #FLUID_OK
|
||||
*/
|
||||
int fluid_midi_event_set_velocity(fluid_midi_event_t* evt, int v)
|
||||
{
|
||||
|
@ -800,7 +798,7 @@ int fluid_midi_event_get_control(fluid_midi_event_t* evt)
|
|||
* Set the control field of a MIDI event structure.
|
||||
* @param evt MIDI event structure
|
||||
* @param v MIDI control number
|
||||
* @return Always returns 0
|
||||
* @return Always returns #FLUID_OK
|
||||
*/
|
||||
int fluid_midi_event_set_control(fluid_midi_event_t* evt, int v)
|
||||
{
|
||||
|
@ -822,7 +820,7 @@ int fluid_midi_event_get_value(fluid_midi_event_t* evt)
|
|||
* Set the value field of a MIDI event structure.
|
||||
* @param evt MIDI event structure
|
||||
* @param v Value to assign
|
||||
* @return Always returns 0
|
||||
* @return Always returns #FLUID_OK
|
||||
*/
|
||||
int fluid_midi_event_set_value(fluid_midi_event_t* evt, int v)
|
||||
{
|
||||
|
@ -844,7 +842,7 @@ int fluid_midi_event_get_program(fluid_midi_event_t* evt)
|
|||
* Set the program field of a MIDI event structure.
|
||||
* @param evt MIDI event structure
|
||||
* @param val MIDI program number (0-127)
|
||||
* @return Always returns 0
|
||||
* @return Always returns #FLUID_OK
|
||||
*/
|
||||
int fluid_midi_event_set_program(fluid_midi_event_t* evt, int val)
|
||||
{
|
||||
|
@ -855,7 +853,7 @@ int fluid_midi_event_set_program(fluid_midi_event_t* evt, int val)
|
|||
/**
|
||||
* Get the pitch field of a MIDI event structure.
|
||||
* @param evt MIDI event structure
|
||||
* @return Pitch value (DOCME units?)
|
||||
* @return Pitch value (14 bit value, 0-16383, 8192 is center)
|
||||
*/
|
||||
int fluid_midi_event_get_pitch(fluid_midi_event_t* evt)
|
||||
{
|
||||
|
@ -865,7 +863,7 @@ int fluid_midi_event_get_pitch(fluid_midi_event_t* evt)
|
|||
/**
|
||||
* Set the pitch field of a MIDI event structure.
|
||||
* @param evt MIDI event structure
|
||||
* @param val Pitch value (DOCME units?)
|
||||
* @param val Pitch value (14 bit value, 0-16383, 8192 is center)
|
||||
* @return Always returns FLUID_OK
|
||||
*/
|
||||
int fluid_midi_event_set_pitch(fluid_midi_event_t* evt, int val)
|
||||
|
@ -882,7 +880,7 @@ int fluid_midi_event_set_pitch(fluid_midi_event_t* evt, int val)
|
|||
* @param dynamic TRUE if the SYSEX data has been dynamically allocated and
|
||||
* should be freed when the event is freed (only applies if event gets destroyed
|
||||
* with delete_fluid_midi_event())
|
||||
* @return Always returns FLUID_OK
|
||||
* @return Always returns #FLUID_OK
|
||||
*
|
||||
* NOTE: Unlike the other event assignment functions, this one sets evt->type.
|
||||
*/
|
||||
|
@ -1134,7 +1132,7 @@ fluid_player_t* new_fluid_player(fluid_synth_t* synth)
|
|||
/**
|
||||
* Delete a MIDI player instance.
|
||||
* @param player MIDI player instance
|
||||
* @return Always returns 0
|
||||
* @return Always returns #FLUID_OK
|
||||
*/
|
||||
int delete_fluid_player(fluid_player_t* player)
|
||||
{
|
||||
|
@ -1363,7 +1361,7 @@ int fluid_player_callback(void* data, unsigned int msec)
|
|||
/**
|
||||
* Activates play mode for a MIDI player if not already playing.
|
||||
* @param player MIDI player instance
|
||||
* @return 0 on success, -1 on failure
|
||||
* @return #FLUID_OK on success, #FLUID_FAILED otherwise
|
||||
*/
|
||||
int fluid_player_play(fluid_player_t* player)
|
||||
{
|
||||
|
@ -1397,7 +1395,7 @@ int fluid_player_play(fluid_player_t* player)
|
|||
/**
|
||||
* Stops a MIDI player.
|
||||
* @param player MIDI player instance
|
||||
* @return Always returns 0
|
||||
* @return Always returns #FLUID_OK
|
||||
*/
|
||||
int fluid_player_stop(fluid_player_t* player)
|
||||
{
|
||||
|
@ -1422,9 +1420,10 @@ int fluid_player_get_status(fluid_player_t* player)
|
|||
/**
|
||||
* Enable looping of a MIDI player
|
||||
* @param player MIDI player instance
|
||||
* @param loop times left to loop the playlist. -1 means loop infinitely.
|
||||
* @return Always returns 0
|
||||
* @param loop Times left to loop the playlist. -1 means loop infinitely.
|
||||
* @return Always returns #FLUID_OK
|
||||
* @since 1.1.0
|
||||
*
|
||||
* For example, if you want to loop the playlist twice, set loop to 2
|
||||
* and call this function before you start the player.
|
||||
*/
|
||||
|
@ -1438,8 +1437,7 @@ int fluid_player_set_loop(fluid_player_t* player, int loop)
|
|||
* Set the tempo of a MIDI player.
|
||||
* @param player MIDI player instance
|
||||
* @param tempo Tempo to set playback speed to (DOCME - Units?)
|
||||
* @return Always returns 0
|
||||
*
|
||||
* @return Always returns #FLUID_OK
|
||||
*/
|
||||
int fluid_player_set_midi_tempo(fluid_player_t* player, int tempo)
|
||||
{
|
||||
|
@ -1458,7 +1456,7 @@ int fluid_player_set_midi_tempo(fluid_player_t* player, int tempo)
|
|||
* Set the tempo of a MIDI player in beats per minute.
|
||||
* @param player MIDI player instance
|
||||
* @param bpm Tempo in beats per minute
|
||||
* @return Always returns 0
|
||||
* @return Always returns #FLUID_OK
|
||||
*/
|
||||
int fluid_player_set_bpm(fluid_player_t* player, int bpm)
|
||||
{
|
||||
|
@ -1468,8 +1466,7 @@ int fluid_player_set_bpm(fluid_player_t* player, int bpm)
|
|||
/**
|
||||
* Wait for a MIDI player to terminate (when done playing).
|
||||
* @param player MIDI player instance
|
||||
* @return 0 on success, -1 otherwise
|
||||
*
|
||||
* @return #FLUID_OK on success, #FLUID_FAILED otherwise
|
||||
*/
|
||||
int fluid_player_join(fluid_player_t* player)
|
||||
{
|
||||
|
@ -1480,8 +1477,6 @@ int fluid_player_join(fluid_player_t* player)
|
|||
while (player->status == FLUID_PLAYER_PLAYING) {
|
||||
#if defined(WIN32)
|
||||
Sleep(10);
|
||||
#elif defined(MACOS9)
|
||||
/* FIXME: How do we sleep in Macos9? */
|
||||
#else
|
||||
usleep(10000);
|
||||
#endif
|
||||
|
|
|
@ -32,8 +32,8 @@
|
|||
* @param event_handler_data Caller defined data pointer which gets passed to 'handler'
|
||||
* @return New MIDI router instance or NULL on error
|
||||
*
|
||||
* A midi handler connects to a midi input
|
||||
* device and forwards incoming midi events to the synthesizer.
|
||||
* The MIDI handler connects to a midi input device and forwards incoming MIDI
|
||||
* events to the synthesizer, after being filtered/modified by the MIDI router.
|
||||
*/
|
||||
fluid_midi_router_t*
|
||||
new_fluid_midi_router(fluid_settings_t* settings, handle_midi_event_func_t handler, void* event_handler_data)
|
||||
|
@ -77,7 +77,7 @@ new_fluid_midi_router(fluid_settings_t* settings, handle_midi_event_func_t handl
|
|||
/**
|
||||
* Delete a MIDI router instance.
|
||||
* @param router MIDI router to delete
|
||||
* @return Always returns 0
|
||||
* @return Always returns #FLUID_OK
|
||||
*/
|
||||
int
|
||||
delete_fluid_midi_router(fluid_midi_router_t* router)
|
||||
|
@ -249,9 +249,11 @@ int fluid_midi_router_end(fluid_midi_router_t* router){
|
|||
|
||||
/**
|
||||
* Handle a MIDI event through a MIDI router instance.
|
||||
* @param data MIDI router instance #fluid_midi_router_t (DOCME why is it a void *?)
|
||||
* @param data MIDI router instance #fluid_midi_router_t, its a void * so that
|
||||
* this function can be used as a callback for other subsystems
|
||||
* (new_fluid_midi_driver() for example).
|
||||
* @param event MIDI event to handle
|
||||
* @return 0 on success, -1 otherwise
|
||||
* @return #FLUID_OK on success, #FLUID_FAILED otherwise
|
||||
*
|
||||
* Purpose: The midi router is called for each event, that is received
|
||||
* via the 'physical' midi input. Each event can trigger an arbitrary number
|
||||
|
@ -260,7 +262,7 @@ int fluid_midi_router_end(fluid_midi_router_t* router){
|
|||
* In default mode, a noteon event is just forwarded to the synth's 'noteon' function,
|
||||
* a 'CC' event to the synth's 'CC' function and so on.
|
||||
*
|
||||
* The router can be used to
|
||||
* The router can be used to:
|
||||
* - filter messages (for example: Pass sustain pedal CCs only to selected channels),
|
||||
* - split the keyboard (noteon with notenr < x: to ch 1, >x to ch 2),
|
||||
* - layer sounds (for each noteon received on ch 1, create a noteon on ch1, ch2, ch3,...)
|
||||
|
@ -817,7 +819,7 @@ void fluid_midi_router_free_unused_rules(fluid_midi_router_t* router)
|
|||
* MIDI event callback function to display event information to stdout
|
||||
* @param data MIDI router instance
|
||||
* @param event MIDI event data
|
||||
* @return 0 on success, -1 otherwise
|
||||
* @return #FLUID_OK on success, #FLUID_FAILED otherwise
|
||||
*
|
||||
* An implementation of the #handle_midi_event_func_t function type, used for
|
||||
* displaying MIDI event information between the MIDI driver and router to
|
||||
|
@ -861,7 +863,7 @@ int fluid_midi_dump_prerouter(void* data, fluid_midi_event_t* event)
|
|||
* MIDI event callback function to display event information to stdout
|
||||
* @param data MIDI router instance
|
||||
* @param event MIDI event data
|
||||
* @return 0 on success, -1 otherwise
|
||||
* @return #FLUID_OK on success, #FLUID_FAILED otherwise
|
||||
*
|
||||
* An implementation of the #handle_midi_event_func_t function type, used for
|
||||
* displaying MIDI event information between the MIDI driver and router to
|
||||
|
|
|
@ -26,23 +26,72 @@
|
|||
#define SAMPLE_LOOP_MARGIN 8
|
||||
|
||||
/* Prototypes */
|
||||
int fluid_rampreset_add_sample(fluid_rampreset_t* preset, fluid_sample_t* sample, int lokey, int hikey);
|
||||
int fluid_rampreset_izone_set_gen(fluid_rampreset_t* preset, fluid_sample_t* sample, int gen_type, float value);
|
||||
int fluid_rampreset_izone_set_loop(fluid_rampreset_t* preset, fluid_sample_t* sample, int on, float loopstart, float loopend);
|
||||
int fluid_rampreset_remove_izone(fluid_rampreset_t* preset, fluid_sample_t* sample);
|
||||
void fluid_rampreset_updatevoices(fluid_rampreset_t* preset, int gen_type, float val);
|
||||
static int fluid_ramsfont_sfont_delete(fluid_sfont_t* sfont);
|
||||
static char *fluid_ramsfont_sfont_get_name(fluid_sfont_t* sfont);
|
||||
static fluid_preset_t *fluid_ramsfont_sfont_get_preset(fluid_sfont_t* sfont,
|
||||
unsigned int bank,
|
||||
unsigned int prenum);
|
||||
static void fluid_ramsfont_sfont_iteration_start(fluid_sfont_t* sfont);
|
||||
static int fluid_ramsfont_sfont_iteration_next(fluid_sfont_t* sfont,
|
||||
fluid_preset_t* preset);
|
||||
static int fluid_rampreset_preset_delete(fluid_preset_t* preset);
|
||||
static char *fluid_rampreset_preset_get_name(fluid_preset_t* preset);
|
||||
static int fluid_rampreset_preset_get_banknum(fluid_preset_t* preset);
|
||||
static int fluid_rampreset_preset_get_num(fluid_preset_t* preset);
|
||||
static int fluid_rampreset_preset_noteon(fluid_preset_t* preset,
|
||||
fluid_synth_t* synth, int chan,
|
||||
int key, int vel);
|
||||
static fluid_ramsfont_t *new_fluid_ramsfont (void);
|
||||
static int delete_fluid_ramsfont (fluid_ramsfont_t* sfont);
|
||||
static char *fluid_ramsfont_get_name(fluid_ramsfont_t* sfont);
|
||||
static int fluid_ramsfont_add_preset (fluid_ramsfont_t* sfont,
|
||||
fluid_rampreset_t* preset);
|
||||
static fluid_rampreset_t *fluid_ramsfont_get_preset (fluid_ramsfont_t* sfont,
|
||||
unsigned int bank, unsigned int num);
|
||||
static void fluid_ramsfont_iteration_start (fluid_ramsfont_t* sfont);
|
||||
static int fluid_ramsfont_iteration_next (fluid_ramsfont_t* sfont,
|
||||
fluid_preset_t* preset);
|
||||
static fluid_rampreset_t* new_fluid_rampreset(fluid_ramsfont_t* sfont);
|
||||
static int delete_fluid_rampreset (fluid_rampreset_t* preset);
|
||||
static int fluid_rampreset_get_banknum (fluid_rampreset_t* preset);
|
||||
static int fluid_rampreset_get_num (fluid_rampreset_t* preset);
|
||||
static char *fluid_rampreset_get_name (fluid_rampreset_t* preset);
|
||||
static fluid_rampreset_t *fluid_rampreset_next (fluid_rampreset_t* preset);
|
||||
static int fluid_rampreset_add_zone(fluid_rampreset_t* preset,
|
||||
fluid_preset_zone_t* zone);
|
||||
static int fluid_rampreset_add_sample (fluid_rampreset_t* preset,
|
||||
fluid_sample_t* sample,
|
||||
int lokey, int hikey);
|
||||
static fluid_inst_zone_t *fluid_rampreset_izoneforsample (fluid_rampreset_t* preset,
|
||||
fluid_sample_t* sample);
|
||||
static int fluid_rampreset_izone_set_loop (fluid_rampreset_t* preset,
|
||||
fluid_sample_t* sample,
|
||||
int on, float loopstart, float loopend);
|
||||
static int fluid_rampreset_izone_set_gen (fluid_rampreset_t* preset,
|
||||
fluid_sample_t* sample,
|
||||
int gen_type, float value);
|
||||
static int fluid_rampreset_remove_izone(fluid_rampreset_t* preset,
|
||||
fluid_sample_t* sample);
|
||||
static int fluid_rampreset_remembervoice (fluid_rampreset_t* preset,
|
||||
fluid_voice_t* voice);
|
||||
static void fluid_rampreset_updatevoices (fluid_rampreset_t* preset,
|
||||
int gen_type, float val);
|
||||
static int fluid_rampreset_noteon (fluid_rampreset_t* preset, fluid_synth_t* synth,
|
||||
int chan, int key, int vel);
|
||||
|
||||
/*
|
||||
* fluid_ramsfont_create_sfont
|
||||
|
||||
/**
|
||||
* Create a #fluid_sfont_t wrapping a #fluid_ramsfont_t
|
||||
* @return New #fluid_sfont_t or NULL if out of memory
|
||||
*/
|
||||
fluid_sfont_t*
|
||||
fluid_ramsfont_create_sfont()
|
||||
{
|
||||
fluid_sfont_t* sfont;
|
||||
fluid_ramsfont_t* ramsfont;
|
||||
fluid_sfont_t* sfont;
|
||||
fluid_ramsfont_t* ramsfont;
|
||||
|
||||
ramsfont = new_fluid_ramsfont();
|
||||
if (ramsfont == NULL) {
|
||||
ramsfont = new_fluid_ramsfont();
|
||||
if (ramsfont == NULL) {
|
||||
return NULL;
|
||||
}
|
||||
|
||||
|
@ -60,28 +109,28 @@ fluid_ramsfont_create_sfont()
|
|||
sfont->iteration_next = fluid_ramsfont_sfont_iteration_next;
|
||||
|
||||
return sfont;
|
||||
|
||||
}
|
||||
|
||||
/***************************************************************
|
||||
*
|
||||
* PUBLIC INTERFACE
|
||||
*/
|
||||
|
||||
int fluid_ramsfont_sfont_delete(fluid_sfont_t* sfont)
|
||||
/* RAM SoundFont loader method to delete SoundFont */
|
||||
static int
|
||||
fluid_ramsfont_sfont_delete(fluid_sfont_t* sfont)
|
||||
{
|
||||
if (delete_fluid_ramsfont(sfont->data) != 0)
|
||||
return -1;
|
||||
FLUID_FREE(sfont);
|
||||
return 0;
|
||||
if (delete_fluid_ramsfont(sfont->data) != 0)
|
||||
return -1;
|
||||
FLUID_FREE(sfont);
|
||||
return 0;
|
||||
}
|
||||
|
||||
char* fluid_ramsfont_sfont_get_name(fluid_sfont_t* sfont)
|
||||
/* RAM SoundFont loader method to get name */
|
||||
static char *
|
||||
fluid_ramsfont_sfont_get_name(fluid_sfont_t* sfont)
|
||||
{
|
||||
return fluid_ramsfont_get_name((fluid_ramsfont_t*) sfont->data);
|
||||
}
|
||||
|
||||
fluid_preset_t* fluid_ramsfont_sfont_get_preset(fluid_sfont_t* sfont, unsigned int bank, unsigned int prenum)
|
||||
/* RAM SoundFont loader method to get a preset */
|
||||
static fluid_preset_t *
|
||||
fluid_ramsfont_sfont_get_preset(fluid_sfont_t* sfont, unsigned int bank, unsigned int prenum)
|
||||
{
|
||||
fluid_preset_t* preset;
|
||||
fluid_rampreset_t* rampreset;
|
||||
|
@ -110,12 +159,16 @@ fluid_preset_t* fluid_ramsfont_sfont_get_preset(fluid_sfont_t* sfont, unsigned i
|
|||
return preset;
|
||||
}
|
||||
|
||||
void fluid_ramsfont_sfont_iteration_start(fluid_sfont_t* sfont)
|
||||
/* RAM SoundFont loader method to start preset iteration */
|
||||
static void
|
||||
fluid_ramsfont_sfont_iteration_start(fluid_sfont_t* sfont)
|
||||
{
|
||||
fluid_ramsfont_iteration_start((fluid_ramsfont_t*) sfont->data);
|
||||
}
|
||||
|
||||
int fluid_ramsfont_sfont_iteration_next(fluid_sfont_t* sfont, fluid_preset_t* preset)
|
||||
/* RAM SoundFont loader method to advance preset iteration */
|
||||
static int
|
||||
fluid_ramsfont_sfont_iteration_next(fluid_sfont_t* sfont, fluid_preset_t* preset)
|
||||
{
|
||||
preset->free = fluid_rampreset_preset_delete;
|
||||
preset->get_name = fluid_rampreset_preset_get_name;
|
||||
|
@ -127,7 +180,9 @@ int fluid_ramsfont_sfont_iteration_next(fluid_sfont_t* sfont, fluid_preset_t* pr
|
|||
return fluid_ramsfont_iteration_next((fluid_ramsfont_t*) sfont->data, preset);
|
||||
}
|
||||
|
||||
int fluid_rampreset_preset_delete(fluid_preset_t* preset)
|
||||
/* RAM SoundFont loader delete preset method */
|
||||
static int
|
||||
fluid_rampreset_preset_delete(fluid_preset_t* preset)
|
||||
{
|
||||
FLUID_FREE(preset);
|
||||
|
||||
|
@ -136,22 +191,30 @@ int fluid_rampreset_preset_delete(fluid_preset_t* preset)
|
|||
return 0;
|
||||
}
|
||||
|
||||
char* fluid_rampreset_preset_get_name(fluid_preset_t* preset)
|
||||
/* RAM SoundFont loader get preset name method */
|
||||
static char *
|
||||
fluid_rampreset_preset_get_name(fluid_preset_t* preset)
|
||||
{
|
||||
return fluid_rampreset_get_name((fluid_rampreset_t*) preset->data);
|
||||
}
|
||||
|
||||
int fluid_rampreset_preset_get_banknum(fluid_preset_t* preset)
|
||||
/* RAM SoundFont loader get preset bank method */
|
||||
static int
|
||||
fluid_rampreset_preset_get_banknum(fluid_preset_t* preset)
|
||||
{
|
||||
return fluid_rampreset_get_banknum((fluid_rampreset_t*) preset->data);
|
||||
}
|
||||
|
||||
int fluid_rampreset_preset_get_num(fluid_preset_t* preset)
|
||||
/* RAM SoundFont loader get preset program method */
|
||||
static int
|
||||
fluid_rampreset_preset_get_num(fluid_preset_t* preset)
|
||||
{
|
||||
return fluid_rampreset_get_num((fluid_rampreset_t*) preset->data);
|
||||
}
|
||||
|
||||
int fluid_rampreset_preset_noteon(fluid_preset_t* preset, fluid_synth_t* synth, int chan, int key, int vel)
|
||||
/* RAM SoundFont loader preset noteon method */
|
||||
static int
|
||||
fluid_rampreset_preset_noteon(fluid_preset_t* preset, fluid_synth_t* synth, int chan, int key, int vel)
|
||||
{
|
||||
return fluid_rampreset_noteon((fluid_rampreset_t*) preset->data, synth, chan, key, vel);
|
||||
}
|
||||
|
@ -164,10 +227,8 @@ int fluid_rampreset_preset_noteon(fluid_preset_t* preset, fluid_synth_t* synth,
|
|||
* SFONT
|
||||
*/
|
||||
|
||||
/*
|
||||
* new_fluid_ramsfont
|
||||
*/
|
||||
fluid_ramsfont_t* new_fluid_ramsfont()
|
||||
static fluid_ramsfont_t *
|
||||
new_fluid_ramsfont (void)
|
||||
{
|
||||
fluid_ramsfont_t* sfont;
|
||||
|
||||
|
@ -184,10 +245,8 @@ fluid_ramsfont_t* new_fluid_ramsfont()
|
|||
return sfont;
|
||||
}
|
||||
|
||||
/*
|
||||
* delete_fluid_ramsfont
|
||||
*/
|
||||
int delete_fluid_ramsfont(fluid_ramsfont_t* sfont)
|
||||
static int
|
||||
delete_fluid_ramsfont (fluid_ramsfont_t* sfont)
|
||||
{
|
||||
fluid_list_t *list;
|
||||
fluid_rampreset_t* preset;
|
||||
|
@ -221,30 +280,29 @@ int delete_fluid_ramsfont(fluid_ramsfont_t* sfont)
|
|||
return FLUID_OK;
|
||||
}
|
||||
|
||||
/*
|
||||
* fluid_ramsfont_get_name
|
||||
*/
|
||||
char* fluid_ramsfont_get_name(fluid_ramsfont_t* sfont)
|
||||
static char *
|
||||
fluid_ramsfont_get_name(fluid_ramsfont_t* sfont)
|
||||
{
|
||||
return sfont->name;
|
||||
}
|
||||
|
||||
/*
|
||||
* fluid_ramsfont_set_name
|
||||
/**
|
||||
* Set a RAM SoundFont name.
|
||||
* @param sfont RAM SoundFont
|
||||
* @param name Name to assign (should be 20 chars in length with a NULL terminator)
|
||||
* @return #FLUID_OK
|
||||
*/
|
||||
int
|
||||
fluid_ramsfont_set_name(fluid_ramsfont_t* sfont, char * name)
|
||||
fluid_ramsfont_set_name (fluid_ramsfont_t *sfont, char *name)
|
||||
{
|
||||
FLUID_MEMCPY(sfont->name, name, 20);
|
||||
return FLUID_OK;
|
||||
}
|
||||
|
||||
|
||||
/* fluid_ramsfont_add_preset
|
||||
*
|
||||
* Add a preset to the SoundFont
|
||||
*/
|
||||
int fluid_ramsfont_add_preset(fluid_ramsfont_t* sfont, fluid_rampreset_t* preset)
|
||||
/* Add a preset to a RAM SoundFont */
|
||||
static int
|
||||
fluid_ramsfont_add_preset (fluid_ramsfont_t* sfont, fluid_rampreset_t* preset)
|
||||
{
|
||||
fluid_rampreset_t *cur, *prev;
|
||||
if (sfont->preset == NULL) {
|
||||
|
@ -275,12 +333,21 @@ int fluid_ramsfont_add_preset(fluid_ramsfont_t* sfont, fluid_rampreset_t* preset
|
|||
return FLUID_OK;
|
||||
}
|
||||
|
||||
/*
|
||||
* fluid_ramsfont_add_ramsample
|
||||
/**
|
||||
* Creates one instrument zone for the sample inside the preset defined by
|
||||
* \a bank and \a num
|
||||
* @param sfont RAM SoundFont
|
||||
* @param bank Preset bank number
|
||||
* @param num Preset program number
|
||||
* @param sample Sample to use for instrument zone
|
||||
* @param lokey Lower MIDI key range of zone (0-127, <= \a hikey)
|
||||
* @param hikey Upper MIDI key range of zone (0-127, >= \a lokey)
|
||||
* @return #FLUID_OK on success, #FLUID_FAILED otherwise
|
||||
*/
|
||||
int fluid_ramsfont_add_izone(fluid_ramsfont_t* sfont,
|
||||
unsigned int bank, unsigned int num, fluid_sample_t* sample,
|
||||
int lokey, int hikey)
|
||||
int
|
||||
fluid_ramsfont_add_izone(fluid_ramsfont_t* sfont, unsigned int bank,
|
||||
unsigned int num, fluid_sample_t* sample,
|
||||
int lokey, int hikey)
|
||||
{
|
||||
/*- find or create a preset
|
||||
- add it the sample using the fluid_rampreset_add_sample fucntion
|
||||
|
@ -320,8 +387,18 @@ int fluid_ramsfont_add_izone(fluid_ramsfont_t* sfont,
|
|||
return FLUID_OK;
|
||||
}
|
||||
|
||||
int fluid_ramsfont_remove_izone(fluid_ramsfont_t* sfont,
|
||||
unsigned int bank, unsigned int num, fluid_sample_t* sample) {
|
||||
/**
|
||||
* Removes the instrument zone corresponding to \a bank, \a num and \a sample
|
||||
* @param sfont RAM SoundFont
|
||||
* @param bank Preset bank number
|
||||
* @param num Preset program number
|
||||
* @param sample Sample of the preset zone
|
||||
* @return #FLUID_OK on success, #FLUID_FAILED otherwise
|
||||
*/
|
||||
int
|
||||
fluid_ramsfont_remove_izone (fluid_ramsfont_t* sfont, unsigned int bank,
|
||||
unsigned int num, fluid_sample_t* sample)
|
||||
{
|
||||
int err;
|
||||
fluid_rampreset_t* preset = fluid_ramsfont_get_preset(sfont, bank, num);
|
||||
if (preset == NULL) {
|
||||
|
@ -340,12 +417,21 @@ int fluid_ramsfont_remove_izone(fluid_ramsfont_t* sfont,
|
|||
return FLUID_OK;
|
||||
}
|
||||
|
||||
|
||||
/* Note for version 2.0 : missing API fluid_ramsfont_izone_get_gen - Antoine Schmitt May 2003 */
|
||||
int fluid_ramsfont_izone_set_gen(fluid_ramsfont_t* sfont,
|
||||
unsigned int bank, unsigned int num, fluid_sample_t* sample,
|
||||
int gen_type, float value) {
|
||||
|
||||
/**
|
||||
* Sets a generator on an instrument zone identified by \a bank, \a num and \a sample
|
||||
* @param sfont RAM SoundFont
|
||||
* @param bank Preset bank number
|
||||
* @param num Preset program number
|
||||
* @param sample Sample of the instrument zone.
|
||||
* @param gen_type Generator ID (#fluid_gen_type)
|
||||
* @param value Generator value
|
||||
* @return #FLUID_OK on success, #FLUID_FAILED otherwise
|
||||
*/
|
||||
int
|
||||
fluid_ramsfont_izone_set_gen (fluid_ramsfont_t* sfont, unsigned int bank,
|
||||
unsigned int num, fluid_sample_t* sample,
|
||||
int gen_type, float value)
|
||||
{
|
||||
fluid_rampreset_t* preset = fluid_ramsfont_get_preset(sfont, bank, num);
|
||||
if (preset == NULL) {
|
||||
return FLUID_FAILED;
|
||||
|
@ -354,10 +440,24 @@ int fluid_ramsfont_izone_set_gen(fluid_ramsfont_t* sfont,
|
|||
return fluid_rampreset_izone_set_gen(preset, sample, gen_type, value);
|
||||
}
|
||||
|
||||
/* Note for version 2.0 : missing API fluid_ramsfont_izone_get_loop - Antoine Schmitt May 2003 */
|
||||
int fluid_ramsfont_izone_set_loop(fluid_ramsfont_t* sfont,
|
||||
unsigned int bank, unsigned int num, fluid_sample_t* sample,
|
||||
int on, float loopstart, float loopend) {
|
||||
/**
|
||||
* Sets loop start/end values of the instrument zone identified by \a bank,
|
||||
* \a num and \a sample.
|
||||
* @param sfont RAM SoundFont
|
||||
* @param bank Preset bank number
|
||||
* @param num Preset program number
|
||||
* @param sample Sample of the instrument zone
|
||||
* @param on TRUE to enable looping, FALSE for one shot (\a loopstart and \a loopend
|
||||
* not used)
|
||||
* @param loopstart Loop start, in frames (counted from 0)
|
||||
* @param loopend Loop end, in frames (counted from last frame, thus is < 0)
|
||||
* @return #FLUID_OK on success, #FLUID_FAILED otherwise
|
||||
*/
|
||||
int
|
||||
fluid_ramsfont_izone_set_loop (fluid_ramsfont_t *sfont, unsigned int bank,
|
||||
unsigned int num, fluid_sample_t* sample,
|
||||
int on, float loopstart, float loopend)
|
||||
{
|
||||
fluid_rampreset_t* preset = fluid_ramsfont_get_preset(sfont, bank, num);
|
||||
if (preset == NULL) {
|
||||
return FLUID_FAILED;
|
||||
|
@ -366,10 +466,9 @@ int fluid_ramsfont_izone_set_loop(fluid_ramsfont_t* sfont,
|
|||
return fluid_rampreset_izone_set_loop(preset, sample, on, loopstart, loopend);
|
||||
}
|
||||
|
||||
/*
|
||||
* fluid_ramsfont_get_preset
|
||||
*/
|
||||
fluid_rampreset_t* fluid_ramsfont_get_preset(fluid_ramsfont_t* sfont, unsigned int bank, unsigned int num)
|
||||
/* Get a preset from a RAM SoundFont */
|
||||
static fluid_rampreset_t *
|
||||
fluid_ramsfont_get_preset (fluid_ramsfont_t* sfont, unsigned int bank, unsigned int num)
|
||||
{
|
||||
fluid_rampreset_t* preset = sfont->preset;
|
||||
while (preset != NULL) {
|
||||
|
@ -381,18 +480,16 @@ fluid_rampreset_t* fluid_ramsfont_get_preset(fluid_ramsfont_t* sfont, unsigned i
|
|||
return NULL;
|
||||
}
|
||||
|
||||
/*
|
||||
* fluid_ramsfont_iteration_start
|
||||
*/
|
||||
void fluid_ramsfont_iteration_start(fluid_ramsfont_t* sfont)
|
||||
/* Start preset iteration in a RAM SoundFont */
|
||||
static void
|
||||
fluid_ramsfont_iteration_start (fluid_ramsfont_t* sfont)
|
||||
{
|
||||
sfont->iter_cur = sfont->preset;
|
||||
}
|
||||
|
||||
/*
|
||||
* fluid_ramsfont_iteration_next
|
||||
*/
|
||||
int fluid_ramsfont_iteration_next(fluid_ramsfont_t* sfont, fluid_preset_t* preset)
|
||||
/* Advance preset iteration in a RAM SoundFont */
|
||||
static int
|
||||
fluid_ramsfont_iteration_next (fluid_ramsfont_t* sfont, fluid_preset_t* preset)
|
||||
{
|
||||
if (sfont->iter_cur == NULL) {
|
||||
return 0;
|
||||
|
@ -414,10 +511,8 @@ struct _fluid_rampreset_voice_t {
|
|||
unsigned int voiceID;
|
||||
};
|
||||
|
||||
/*
|
||||
* new_fluid_rampreset
|
||||
*/
|
||||
fluid_rampreset_t*
|
||||
/* Create a new RAM SoundFont preset */
|
||||
static fluid_rampreset_t*
|
||||
new_fluid_rampreset(fluid_ramsfont_t* sfont)
|
||||
{
|
||||
fluid_rampreset_t* preset = FLUID_NEW(fluid_rampreset_t);
|
||||
|
@ -436,11 +531,9 @@ new_fluid_rampreset(fluid_ramsfont_t* sfont)
|
|||
return preset;
|
||||
}
|
||||
|
||||
/*
|
||||
* delete_fluid_rampreset
|
||||
*/
|
||||
int
|
||||
delete_fluid_rampreset(fluid_rampreset_t* preset)
|
||||
/* Delete a RAM SoundFont preset */
|
||||
static int
|
||||
delete_fluid_rampreset (fluid_rampreset_t* preset)
|
||||
{
|
||||
int err = FLUID_OK;
|
||||
fluid_preset_zone_t* zone;
|
||||
|
@ -478,38 +571,37 @@ delete_fluid_rampreset(fluid_rampreset_t* preset)
|
|||
return err;
|
||||
}
|
||||
|
||||
int
|
||||
fluid_rampreset_get_banknum(fluid_rampreset_t* preset)
|
||||
/* Get a RAM SoundFont preset bank */
|
||||
static int
|
||||
fluid_rampreset_get_banknum (fluid_rampreset_t* preset)
|
||||
{
|
||||
return preset->bank;
|
||||
}
|
||||
|
||||
int
|
||||
fluid_rampreset_get_num(fluid_rampreset_t* preset)
|
||||
/* Get a RAM SoundFont preset program */
|
||||
static int
|
||||
fluid_rampreset_get_num (fluid_rampreset_t* preset)
|
||||
{
|
||||
return preset->num;
|
||||
}
|
||||
|
||||
char*
|
||||
fluid_rampreset_get_name(fluid_rampreset_t* preset)
|
||||
/* Get a RAM SoundFont preset name */
|
||||
static char *
|
||||
fluid_rampreset_get_name (fluid_rampreset_t* preset)
|
||||
{
|
||||
return preset->name;
|
||||
}
|
||||
|
||||
/*
|
||||
* fluid_rampreset_next
|
||||
*/
|
||||
fluid_rampreset_t*
|
||||
fluid_rampreset_next(fluid_rampreset_t* preset)
|
||||
/* Advance to next preset */
|
||||
static fluid_rampreset_t *
|
||||
fluid_rampreset_next (fluid_rampreset_t* preset)
|
||||
{
|
||||
return preset->next;
|
||||
}
|
||||
|
||||
|
||||
/*
|
||||
* fluid_rampreset_add_zone
|
||||
*/
|
||||
int
|
||||
/* Add a zone to a RAM SoundFont preset */
|
||||
static int
|
||||
fluid_rampreset_add_zone(fluid_rampreset_t* preset, fluid_preset_zone_t* zone)
|
||||
{
|
||||
if (preset->zone == NULL) {
|
||||
|
@ -522,11 +614,10 @@ fluid_rampreset_add_zone(fluid_rampreset_t* preset, fluid_preset_zone_t* zone)
|
|||
return FLUID_OK;
|
||||
}
|
||||
|
||||
|
||||
/*
|
||||
* fluid_rampreset_add_sample
|
||||
*/
|
||||
int fluid_rampreset_add_sample(fluid_rampreset_t* preset, fluid_sample_t* sample, int lokey, int hikey)
|
||||
/* Add a sample to a RAM SoundFont preset */
|
||||
static int
|
||||
fluid_rampreset_add_sample (fluid_rampreset_t* preset, fluid_sample_t* sample,
|
||||
int lokey, int hikey)
|
||||
{
|
||||
/* create a new instrument zone, with the given sample */
|
||||
|
||||
|
@ -572,7 +663,9 @@ int fluid_rampreset_add_sample(fluid_rampreset_t* preset, fluid_sample_t* sample
|
|||
return FLUID_OK;
|
||||
}
|
||||
|
||||
fluid_inst_zone_t* fluid_rampreset_izoneforsample(fluid_rampreset_t* preset, fluid_sample_t* sample)
|
||||
/* Find an instrument zone with the given sample */
|
||||
static fluid_inst_zone_t *
|
||||
fluid_rampreset_izoneforsample (fluid_rampreset_t* preset, fluid_sample_t* sample)
|
||||
{
|
||||
fluid_inst_t* inst;
|
||||
fluid_inst_zone_t* izone;
|
||||
|
@ -589,8 +682,11 @@ fluid_inst_zone_t* fluid_rampreset_izoneforsample(fluid_rampreset_t* preset, flu
|
|||
return NULL;
|
||||
}
|
||||
|
||||
int fluid_rampreset_izone_set_loop(fluid_rampreset_t* preset, fluid_sample_t* sample,
|
||||
int on, float loopstart, float loopend) {
|
||||
/* Set loop of an instrument zone */
|
||||
static int
|
||||
fluid_rampreset_izone_set_loop (fluid_rampreset_t* preset, fluid_sample_t* sample,
|
||||
int on, float loopstart, float loopend)
|
||||
{
|
||||
fluid_inst_zone_t* izone = fluid_rampreset_izoneforsample(preset, sample);
|
||||
short coarse, fine;
|
||||
|
||||
|
@ -602,7 +698,7 @@ int fluid_rampreset_izone_set_loop(fluid_rampreset_t* preset, fluid_sample_t* sa
|
|||
izone->gen[GEN_SAMPLEMODE].val = FLUID_UNLOOPED;
|
||||
fluid_rampreset_updatevoices(preset, GEN_SAMPLEMODE, FLUID_UNLOOPED);
|
||||
return FLUID_OK;
|
||||
}
|
||||
}
|
||||
|
||||
/* NOTE : We should check that (sample->startloop + loopStart <= sample->endloop - loopend - 32) */
|
||||
|
||||
|
@ -656,8 +752,11 @@ int fluid_rampreset_izone_set_loop(fluid_rampreset_t* preset, fluid_sample_t* sa
|
|||
return FLUID_OK;
|
||||
}
|
||||
|
||||
int fluid_rampreset_izone_set_gen(fluid_rampreset_t* preset, fluid_sample_t* sample,
|
||||
int gen_type, float value) {
|
||||
/* Set a generator on the instrument zone in preset having sample */
|
||||
static int
|
||||
fluid_rampreset_izone_set_gen (fluid_rampreset_t* preset, fluid_sample_t* sample,
|
||||
int gen_type, float value)
|
||||
{
|
||||
fluid_inst_zone_t* izone = fluid_rampreset_izoneforsample(preset, sample);
|
||||
if (izone == NULL)
|
||||
return FLUID_FAILED;
|
||||
|
@ -670,7 +769,10 @@ int fluid_rampreset_izone_set_gen(fluid_rampreset_t* preset, fluid_sample_t* sam
|
|||
return FLUID_OK;
|
||||
}
|
||||
|
||||
int fluid_rampreset_remove_izone(fluid_rampreset_t* preset, fluid_sample_t* sample) {
|
||||
/* Remove the instrument zone from preset having sample */
|
||||
static int
|
||||
fluid_rampreset_remove_izone(fluid_rampreset_t* preset, fluid_sample_t* sample)
|
||||
{
|
||||
fluid_inst_t* inst;
|
||||
fluid_inst_zone_t* izone, * prev;
|
||||
int found = 0;
|
||||
|
@ -718,14 +820,12 @@ int fluid_rampreset_remove_izone(fluid_rampreset_t* preset, fluid_sample_t* samp
|
|||
return FLUID_OK;
|
||||
}
|
||||
|
||||
/*
|
||||
* fluid_rampreset_remembervoice
|
||||
*/
|
||||
int
|
||||
fluid_rampreset_remembervoice(fluid_rampreset_t* preset, fluid_voice_t* voice) {
|
||||
/* stores the voice and the its ID in the preset for later update on gen_set */
|
||||
fluid_rampreset_voice_t *presetvoice = FLUID_NEW(fluid_rampreset_voice_t);
|
||||
if (presetvoice == NULL) {
|
||||
/* Stores the voice and the its ID in the preset for later update on gen_set */
|
||||
static int
|
||||
fluid_rampreset_remembervoice (fluid_rampreset_t* preset, fluid_voice_t* voice)
|
||||
{
|
||||
fluid_rampreset_voice_t *presetvoice = FLUID_NEW(fluid_rampreset_voice_t);
|
||||
if (presetvoice == NULL) {
|
||||
FLUID_LOG(FLUID_ERR, "Out of memory");
|
||||
return FLUID_FAILED;
|
||||
}
|
||||
|
@ -742,16 +842,15 @@ fluid_rampreset_remembervoice(fluid_rampreset_t* preset, fluid_voice_t* voice) {
|
|||
return FLUID_OK;
|
||||
}
|
||||
|
||||
/*
|
||||
* fluid_rampreset_updatevoice
|
||||
*/
|
||||
void
|
||||
fluid_rampreset_updatevoices(fluid_rampreset_t* preset, int gen_type, float val) {
|
||||
/* Update a generator in realtime for a preset */
|
||||
static void
|
||||
fluid_rampreset_updatevoices (fluid_rampreset_t* preset, int gen_type, float val)
|
||||
{
|
||||
fluid_list_t *tmp = preset->presetvoices, *prev = NULL, *next;
|
||||
|
||||
/* walk the presetvoice to update them if they are still active and ours.
|
||||
If their ID has changed or their state is not playing, they are not ours, so we forget them
|
||||
*/
|
||||
/* Walk the presetvoice to update them if they are still active and ours.
|
||||
* If their ID has changed or their state is not playing, they are not
|
||||
* ours, so we forget them. */
|
||||
while (tmp) {
|
||||
fluid_rampreset_voice_t *presetvoice = (fluid_rampreset_voice_t *)(tmp->data);
|
||||
fluid_voice_t *voice = presetvoice->voice;
|
||||
|
@ -783,11 +882,10 @@ fluid_rampreset_updatevoices(fluid_rampreset_t* preset, int gen_type, float val)
|
|||
}
|
||||
|
||||
|
||||
/*
|
||||
* fluid_rampreset_noteon
|
||||
*/
|
||||
int
|
||||
fluid_rampreset_noteon(fluid_rampreset_t* preset, fluid_synth_t* synth, int chan, int key, int vel)
|
||||
/* RAM SoundFont preset note on */
|
||||
static int
|
||||
fluid_rampreset_noteon (fluid_rampreset_t* preset, fluid_synth_t* synth, int chan,
|
||||
int key, int vel)
|
||||
{
|
||||
fluid_preset_zone_t *preset_zone;
|
||||
fluid_inst_t* inst;
|
||||
|
@ -1011,22 +1109,34 @@ fluid_rampreset_noteon(fluid_rampreset_t* preset, fluid_synth_t* synth, int chan
|
|||
*/
|
||||
|
||||
|
||||
|
||||
/*
|
||||
* fluid_sample_set_name
|
||||
/**
|
||||
* Set the name of a RAM SoundFont sample.
|
||||
* @param sample RAM SoundFont sample
|
||||
* @param name Name to assign to sample (20 chars in length, 0 terminated)
|
||||
* @return #FLUID_OK
|
||||
*/
|
||||
int
|
||||
fluid_sample_set_name(fluid_sample_t* sample, char * name)
|
||||
fluid_sample_set_name(fluid_sample_t* sample, char* name)
|
||||
{
|
||||
FLUID_MEMCPY(sample->name, name, 20);
|
||||
return FLUID_OK;
|
||||
}
|
||||
|
||||
/*
|
||||
* fluid_sample_set_sound_data
|
||||
/**
|
||||
* Assign sample data to a RAM SoundFont sample.
|
||||
* @param sample RAM SoundFont sample
|
||||
* @param data Buffer containing 16 bit audio sample data
|
||||
* @param nbframes Number of samples in \a data
|
||||
* @param copy_data TRUE to copy the data, FALSE to use it directly
|
||||
* @param rootkey Root MIDI note of sample (0-127)
|
||||
* @return #FLUID_OK on success, #FLUID_FAILED otherwise
|
||||
*
|
||||
* WARNING: If \a copy_data is FALSE, data should have 8 unused frames at start
|
||||
* and 8 unused frames at the end.
|
||||
*/
|
||||
int
|
||||
fluid_sample_set_sound_data(fluid_sample_t* sample, short *data, unsigned int nbframes, short copy_data, int rootkey)
|
||||
fluid_sample_set_sound_data (fluid_sample_t* sample, short *data,
|
||||
unsigned int nbframes, short copy_data, int rootkey)
|
||||
{
|
||||
/* 16 bit mono 44.1KHz data in */
|
||||
/* in all cases, the sample has ownership of the data : it will release it in the end */
|
||||
|
@ -1081,11 +1191,12 @@ fluid_sample_set_sound_data(fluid_sample_t* sample, short *data, unsigned int nb
|
|||
return FLUID_OK;
|
||||
}
|
||||
|
||||
/*
|
||||
* new_fluid_ramsample
|
||||
/**
|
||||
* Create new RAM SoundFont sample.
|
||||
* @return New RAM SoundFont sample or NULL if out of memory
|
||||
*/
|
||||
fluid_sample_t*
|
||||
new_fluid_ramsample()
|
||||
fluid_sample_t *
|
||||
new_fluid_ramsample (void)
|
||||
{
|
||||
/* same as new_fluid_sample. Only here so that it is exported */
|
||||
fluid_sample_t* sample = NULL;
|
||||
|
@ -1101,11 +1212,13 @@ new_fluid_ramsample()
|
|||
return sample;
|
||||
}
|
||||
|
||||
/*
|
||||
* delete_fluid_ramsample
|
||||
/**
|
||||
* Delete a RAM SoundFont sample.
|
||||
* @param sample Sample to delete
|
||||
* @return #FLUID_OK
|
||||
*/
|
||||
int
|
||||
delete_fluid_ramsample(fluid_sample_t* sample)
|
||||
delete_fluid_ramsample (fluid_sample_t* sample)
|
||||
{
|
||||
/* same as delete_fluid_sample, plus frees the data */
|
||||
if (sample->data != NULL) {
|
||||
|
|
|
@ -34,28 +34,7 @@ extern "C" {
|
|||
#endif
|
||||
|
||||
|
||||
|
||||
/*
|
||||
|
||||
Public interface
|
||||
|
||||
*/
|
||||
|
||||
int fluid_ramsfont_sfont_delete(fluid_sfont_t* sfont);
|
||||
char* fluid_ramsfont_sfont_get_name(fluid_sfont_t* sfont);
|
||||
fluid_preset_t* fluid_ramsfont_sfont_get_preset(fluid_sfont_t* sfont, unsigned int bank, unsigned int prenum);
|
||||
void fluid_ramsfont_sfont_iteration_start(fluid_sfont_t* sfont);
|
||||
int fluid_ramsfont_sfont_iteration_next(fluid_sfont_t* sfont, fluid_preset_t* preset);
|
||||
|
||||
|
||||
int fluid_rampreset_preset_delete(fluid_preset_t* preset);
|
||||
char* fluid_rampreset_preset_get_name(fluid_preset_t* preset);
|
||||
int fluid_rampreset_preset_get_banknum(fluid_preset_t* preset);
|
||||
int fluid_rampreset_preset_get_num(fluid_preset_t* preset);
|
||||
int fluid_rampreset_preset_noteon(fluid_preset_t* preset, fluid_synth_t* synth, int chan, int key, int vel);
|
||||
|
||||
|
||||
/*
|
||||
/*
|
||||
* fluid_ramsfont_t
|
||||
*/
|
||||
struct _fluid_ramsfont_t
|
||||
|
@ -68,17 +47,6 @@ struct _fluid_ramsfont_t
|
|||
fluid_rampreset_t* iter_cur; /* the current preset in the iteration */
|
||||
};
|
||||
|
||||
/* interface */
|
||||
fluid_ramsfont_t* new_fluid_ramsfont(void);
|
||||
int delete_fluid_ramsfont(fluid_ramsfont_t* sfont);
|
||||
char* fluid_ramsfont_get_name(fluid_ramsfont_t* sfont);
|
||||
fluid_rampreset_t* fluid_ramsfont_get_preset(fluid_ramsfont_t* sfont, unsigned int bank, unsigned int prenum);
|
||||
void fluid_ramsfont_iteration_start(fluid_ramsfont_t* sfont);
|
||||
int fluid_ramsfont_iteration_next(fluid_ramsfont_t* sfont, fluid_preset_t* preset);
|
||||
/* specific */
|
||||
|
||||
|
||||
|
||||
/*
|
||||
* fluid_preset_t
|
||||
*/
|
||||
|
@ -94,18 +62,6 @@ struct _fluid_rampreset_t
|
|||
fluid_list_t *presetvoices; /* chained list of used voices */
|
||||
};
|
||||
|
||||
/* interface */
|
||||
fluid_rampreset_t* new_fluid_rampreset(fluid_ramsfont_t* sfont);
|
||||
int delete_fluid_rampreset(fluid_rampreset_t* preset);
|
||||
fluid_rampreset_t* fluid_rampreset_next(fluid_rampreset_t* preset);
|
||||
char* fluid_rampreset_get_name(fluid_rampreset_t* preset);
|
||||
int fluid_rampreset_get_banknum(fluid_rampreset_t* preset);
|
||||
int fluid_rampreset_get_num(fluid_rampreset_t* preset);
|
||||
int fluid_rampreset_noteon(fluid_rampreset_t* preset, fluid_synth_t* synth, int chan, int key, int vel);
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
#ifdef __cplusplus
|
||||
}
|
||||
|
|
|
@ -74,36 +74,41 @@ typedef struct _fluid_sequencer_client_t {
|
|||
} fluid_sequencer_client_t;
|
||||
|
||||
/* prototypes */
|
||||
/* sorting API */
|
||||
short _fluid_seq_queue_init(fluid_sequencer_t* seq, int nbEvents);
|
||||
void _fluid_seq_queue_end(fluid_sequencer_t* seq);
|
||||
short _fluid_seq_queue_pre_insert(fluid_sequencer_t* seq, fluid_event_t * evt);
|
||||
void _fluid_seq_queue_pre_remove(fluid_sequencer_t* seq, short src, short dest, int type);
|
||||
int _fluid_seq_queue_process(void* data, unsigned int msec); // callback from timer
|
||||
static short _fluid_seq_queue_init(fluid_sequencer_t* seq, int nbEvents);
|
||||
static void _fluid_seq_queue_end(fluid_sequencer_t* seq);
|
||||
static short _fluid_seq_queue_pre_insert(fluid_sequencer_t* seq, fluid_event_t * evt);
|
||||
static void _fluid_seq_queue_pre_remove(fluid_sequencer_t* seq, short src, short dest, int type);
|
||||
static int _fluid_seq_queue_process(void* data, unsigned int msec); // callback from timer
|
||||
static void _fluid_seq_queue_insert_entry(fluid_sequencer_t* seq, fluid_evt_entry * evtentry);
|
||||
static void _fluid_seq_queue_remove_entries_matching(fluid_sequencer_t* seq, fluid_evt_entry* temp);
|
||||
static void _fluid_seq_queue_send_queued_events(fluid_sequencer_t* seq);
|
||||
static void _fluid_free_evt_queue(fluid_evt_entry** first, fluid_evt_entry** last);
|
||||
|
||||
|
||||
/* API implementation */
|
||||
|
||||
/**
|
||||
* Legacy call to new_fluid_sequencer to provide backwards compatibility.
|
||||
* Please use new_fluid_sequencer2 instead.
|
||||
* @deprecated
|
||||
* Create a new sequencer object which uses the system timer. Use
|
||||
* new_fluid_sequencer2() to specify whether the system timer or
|
||||
* fluid_sequencer_process() is used to advance the sequencer.
|
||||
* @return New sequencer instance
|
||||
*/
|
||||
fluid_sequencer_t*
|
||||
new_fluid_sequencer()
|
||||
new_fluid_sequencer (void)
|
||||
{
|
||||
return new_fluid_sequencer2(1);
|
||||
return new_fluid_sequencer2 (TRUE);
|
||||
}
|
||||
|
||||
/**
|
||||
* Create a new sequencer object.
|
||||
* @param useSystemTimer if this parameter is non-zero, sequencer will advance
|
||||
* at the rate of the computer's system clock. If zero, call fluid_sequencer_process
|
||||
* to advance the sequencer.
|
||||
* @param use_system_timer If TRUE, sequencer will advance at the rate of the
|
||||
* system clock. If FALSE, call fluid_sequencer_process() to advance
|
||||
* the sequencer.
|
||||
* @return New sequencer instance
|
||||
* @since 1.1.0
|
||||
*/
|
||||
fluid_sequencer_t*
|
||||
new_fluid_sequencer2(int useSystemTimer)
|
||||
new_fluid_sequencer2 (int use_system_timer)
|
||||
{
|
||||
fluid_sequencer_t* seq;
|
||||
|
||||
|
@ -116,7 +121,7 @@ new_fluid_sequencer2(int useSystemTimer)
|
|||
FLUID_MEMSET(seq, 0, sizeof(fluid_sequencer_t));
|
||||
|
||||
seq->scale = 1000; // default value
|
||||
seq->useSystemTimer = useSystemTimer ? TRUE : FALSE;
|
||||
seq->useSystemTimer = use_system_timer ? TRUE : FALSE;
|
||||
seq->startMs = seq->useSystemTimer ? fluid_curtime() : 0;
|
||||
seq->clients = NULL;
|
||||
seq->clientsID = 0;
|
||||
|
@ -142,8 +147,12 @@ new_fluid_sequencer2(int useSystemTimer)
|
|||
return(seq);
|
||||
}
|
||||
|
||||
/**
|
||||
* Free a sequencer object.
|
||||
* @param seq Sequencer to delete
|
||||
*/
|
||||
void
|
||||
delete_fluid_sequencer(fluid_sequencer_t* seq)
|
||||
delete_fluid_sequencer (fluid_sequencer_t* seq)
|
||||
{
|
||||
|
||||
if (seq == NULL) {
|
||||
|
@ -179,11 +188,13 @@ delete_fluid_sequencer(fluid_sequencer_t* seq)
|
|||
}
|
||||
|
||||
/**
|
||||
* @return 1 if system timers are enabled, or 0 if system timers are disabled.
|
||||
* Check if a sequencer is using the system timer or not.
|
||||
* @param seq Sequencer object
|
||||
* @return TRUE if system timer is being used, FALSE otherwise.
|
||||
* @since 1.1.0
|
||||
*/
|
||||
int
|
||||
fluid_sequencer_get_useSystemTimer(fluid_sequencer_t* seq)
|
||||
fluid_sequencer_get_use_system_timer (fluid_sequencer_t* seq)
|
||||
{
|
||||
return seq->useSystemTimer ? 1 : 0;
|
||||
}
|
||||
|
@ -216,12 +227,20 @@ fluid_seq_dotrace(fluid_sequencer_t* seq, char *fmt, ...)
|
|||
return;
|
||||
}
|
||||
|
||||
/**
|
||||
* Clear sequencer trace buffer.
|
||||
* @param seq Sequencer object
|
||||
*/
|
||||
void
|
||||
fluid_seq_cleartrace(fluid_sequencer_t* seq)
|
||||
{
|
||||
seq->traceptr = seq->tracebuf;
|
||||
}
|
||||
|
||||
/**
|
||||
* Get sequencer trace buffer.
|
||||
* @param seq Sequencer object
|
||||
*/
|
||||
char *
|
||||
fluid_seq_gettrace(fluid_sequencer_t* seq)
|
||||
{
|
||||
|
@ -235,22 +254,34 @@ void fluid_seq_dotrace(fluid_sequencer_t* seq, char *fmt, ...) {}
|
|||
|
||||
/* clients */
|
||||
|
||||
short fluid_sequencer_register_client(fluid_sequencer_t* seq, char* name,
|
||||
fluid_event_callback_t callback, void* data) {
|
||||
|
||||
/**
|
||||
* Register a sequencer client.
|
||||
* @param seq Sequencer object
|
||||
* @param name Name of sequencer client
|
||||
* @param callback Sequencer client callback or NULL for a source client.
|
||||
* @param data User data to pass to the \a callback
|
||||
* @return Unique sequencer ID or #FLUID_FAILED on error
|
||||
*
|
||||
* Clients can be sources or destinations of events. Sources don't need to
|
||||
* register a callback.
|
||||
*/
|
||||
short
|
||||
fluid_sequencer_register_client (fluid_sequencer_t* seq, char* name,
|
||||
fluid_event_callback_t callback, void* data)
|
||||
{
|
||||
fluid_sequencer_client_t * client;
|
||||
char * nameCopy;
|
||||
|
||||
client = FLUID_NEW(fluid_sequencer_client_t);
|
||||
if (client == NULL) {
|
||||
fluid_log(FLUID_PANIC, "sequencer: Out of memory\n");
|
||||
return -1;
|
||||
return FLUID_FAILED;
|
||||
}
|
||||
|
||||
nameCopy = FLUID_STRDUP(name);
|
||||
if (nameCopy == NULL) {
|
||||
fluid_log(FLUID_PANIC, "sequencer: Out of memory\n");
|
||||
return -1;
|
||||
return FLUID_FAILED;
|
||||
}
|
||||
|
||||
seq->clientsID++;
|
||||
|
@ -265,8 +296,13 @@ short fluid_sequencer_register_client(fluid_sequencer_t* seq, char* name,
|
|||
return (client->id);
|
||||
}
|
||||
|
||||
/** Unregister a previously registered client. */
|
||||
void fluid_sequencer_unregister_client(fluid_sequencer_t* seq, short id)
|
||||
/**
|
||||
* Unregister a previously registered client.
|
||||
* @param seq Sequencer object
|
||||
* @param id Client ID as returned by fluid_sequencer_register_client().
|
||||
*/
|
||||
void
|
||||
fluid_sequencer_unregister_client (fluid_sequencer_t* seq, short id)
|
||||
{
|
||||
fluid_list_t *tmp;
|
||||
fluid_event_t* evt;
|
||||
|
@ -302,27 +338,45 @@ void fluid_sequencer_unregister_client(fluid_sequencer_t* seq, short id)
|
|||
return;
|
||||
}
|
||||
|
||||
int fluid_sequencer_count_clients(fluid_sequencer_t* seq)
|
||||
/**
|
||||
* Count a sequencers registered clients.
|
||||
* @param seq Sequencer object
|
||||
* @return Count of sequencer clients.
|
||||
*/
|
||||
int
|
||||
fluid_sequencer_count_clients(fluid_sequencer_t* seq)
|
||||
{
|
||||
if (seq->clients == NULL)
|
||||
return 0;
|
||||
return fluid_list_size(seq->clients);
|
||||
}
|
||||
|
||||
/** Returns the id of a registered client. */
|
||||
short fluid_sequencer_get_client_id(fluid_sequencer_t* seq, int index)
|
||||
/**
|
||||
* Get a client ID from its index (order in which it was registered).
|
||||
* @param seq Sequencer object
|
||||
* @param index Index of register client
|
||||
* @return Client ID or #FLUID_FAILED if not found
|
||||
*/
|
||||
short fluid_sequencer_get_client_id (fluid_sequencer_t* seq, int index)
|
||||
{
|
||||
fluid_list_t *tmp = fluid_list_nth(seq->clients, index);
|
||||
if (tmp == NULL) {
|
||||
return -1;
|
||||
return FLUID_FAILED;
|
||||
} else {
|
||||
fluid_sequencer_client_t *client = (fluid_sequencer_client_t*)tmp->data;
|
||||
return client->id;
|
||||
}
|
||||
}
|
||||
|
||||
/** Returns the name of a registered client. */
|
||||
char* fluid_sequencer_get_client_name(fluid_sequencer_t* seq, int id)
|
||||
/**
|
||||
* Get the name of a registered client.
|
||||
* @param seq Sequencer object
|
||||
* @param id Client ID
|
||||
* @return Client name or NULL if not found. String is internal and should not
|
||||
* be modified or freed.
|
||||
*/
|
||||
char *
|
||||
fluid_sequencer_get_client_name(fluid_sequencer_t* seq, int id)
|
||||
{
|
||||
fluid_list_t *tmp;
|
||||
|
||||
|
@ -341,11 +395,18 @@ char* fluid_sequencer_get_client_name(fluid_sequencer_t* seq, int id)
|
|||
return NULL;
|
||||
}
|
||||
|
||||
int fluid_sequencer_client_is_dest(fluid_sequencer_t* seq, int id)
|
||||
/**
|
||||
* Check if a client is a destination client.
|
||||
* @param seq Sequencer object
|
||||
* @param id Client ID
|
||||
* @return TRUE if client is a destination client, FALSE otherwise or if not found
|
||||
*/
|
||||
int
|
||||
fluid_sequencer_client_is_dest(fluid_sequencer_t* seq, int id)
|
||||
{
|
||||
fluid_list_t *tmp;
|
||||
|
||||
if (seq->clients == NULL) return 0;
|
||||
if (seq->clients == NULL) return FALSE;
|
||||
|
||||
tmp = seq->clients;
|
||||
while (tmp) {
|
||||
|
@ -356,11 +417,17 @@ int fluid_sequencer_client_is_dest(fluid_sequencer_t* seq, int id)
|
|||
|
||||
tmp = tmp->next;
|
||||
}
|
||||
return 0;
|
||||
return FALSE;
|
||||
}
|
||||
|
||||
/* sending events */
|
||||
void fluid_sequencer_send_now(fluid_sequencer_t* seq, fluid_event_t* evt)
|
||||
/**
|
||||
* Send an event immediately.
|
||||
* @param seq Sequencer object
|
||||
* @param evt Event to send (copied)
|
||||
*/
|
||||
/* Event not actually copied, but since its used immediately it virtually is. */
|
||||
void
|
||||
fluid_sequencer_send_now(fluid_sequencer_t* seq, fluid_event_t* evt)
|
||||
{
|
||||
short destID = fluid_event_get_dest(evt);
|
||||
|
||||
|
@ -379,9 +446,18 @@ void fluid_sequencer_send_now(fluid_sequencer_t* seq, fluid_event_t* evt)
|
|||
}
|
||||
}
|
||||
|
||||
|
||||
/**
|
||||
* Schedule an event for sending at a later time.
|
||||
* @param seq Sequencer object
|
||||
* @param evt Event to send
|
||||
* @param time Time value in ticks (in milliseconds with the default time scale of 1000).
|
||||
* @param absolute TRUE if \a time is absolute sequencer time (time since sequencer
|
||||
* creation), FALSE if relative to current time.
|
||||
* @return #FLUID_OK on success, #FLUID_FAILED otherwise
|
||||
*/
|
||||
int
|
||||
fluid_sequencer_send_at(fluid_sequencer_t* seq, fluid_event_t* evt, unsigned int time, int absolute)
|
||||
fluid_sequencer_send_at (fluid_sequencer_t* seq, fluid_event_t* evt,
|
||||
unsigned int time, int absolute)
|
||||
{
|
||||
unsigned int now = fluid_sequencer_get_tick(seq);
|
||||
|
||||
|
@ -392,25 +468,20 @@ fluid_sequencer_send_at(fluid_sequencer_t* seq, fluid_event_t* evt, unsigned int
|
|||
/* time stamp event */
|
||||
fluid_event_set_time(evt, time);
|
||||
|
||||
/* process late */
|
||||
/* Commented out for thread safety - send_at must go via the queue */
|
||||
/* if (time < now) {
|
||||
fluid_sequencer_send_now(seq, evt);
|
||||
return 0;
|
||||
}*/
|
||||
|
||||
/* process now */
|
||||
/* if (time == now) {
|
||||
fluid_sequencer_send_now(seq, evt);
|
||||
return 0;
|
||||
}*/
|
||||
|
||||
/* queue for processing later */
|
||||
return _fluid_seq_queue_pre_insert(seq, evt);
|
||||
}
|
||||
|
||||
/**
|
||||
* Remove events from the event queue.
|
||||
* @param seq Sequencer object
|
||||
* @param source Source client ID to match or -1 for wildcard
|
||||
* @param dest Destination client ID to match or -1 for wildcard
|
||||
* @param type Event type to match or -1 for wildcard (#fluid_seq_event_type)
|
||||
*/
|
||||
void
|
||||
fluid_sequencer_remove_events(fluid_sequencer_t* seq, short source, short dest, int type)
|
||||
fluid_sequencer_remove_events (fluid_sequencer_t* seq, short source,
|
||||
short dest, int type)
|
||||
{
|
||||
_fluid_seq_queue_pre_remove(seq, source, dest, type);
|
||||
}
|
||||
|
@ -419,7 +490,14 @@ fluid_sequencer_remove_events(fluid_sequencer_t* seq, short source, short dest,
|
|||
/*************************************
|
||||
time
|
||||
**************************************/
|
||||
unsigned int fluid_sequencer_get_tick(fluid_sequencer_t* seq)
|
||||
|
||||
/**
|
||||
* Get the current tick of a sequencer.
|
||||
* @param seq Sequencer object
|
||||
* @return Current tick value
|
||||
*/
|
||||
unsigned int
|
||||
fluid_sequencer_get_tick (fluid_sequencer_t* seq)
|
||||
{
|
||||
unsigned int absMs = seq->useSystemTimer ? (int) fluid_curtime() : g_atomic_int_get(&seq->currentMs);
|
||||
double nowFloat;
|
||||
|
@ -429,7 +507,17 @@ unsigned int fluid_sequencer_get_tick(fluid_sequencer_t* seq)
|
|||
return now;
|
||||
}
|
||||
|
||||
void fluid_sequencer_set_time_scale(fluid_sequencer_t* seq, double scale)
|
||||
/**
|
||||
* Set the time scale of a sequencer.
|
||||
* @param seq Sequencer object
|
||||
* @param scale Sequencer scale value in ticks per second
|
||||
* (default is 1000 for 1 tick per millisecond, max is 1000.0)
|
||||
*
|
||||
* If there are already scheduled events in the sequencer and the scale is changed
|
||||
* the events are adjusted accordingly.
|
||||
*/
|
||||
void
|
||||
fluid_sequencer_set_time_scale (fluid_sequencer_t* seq, double scale)
|
||||
{
|
||||
if (scale <= 0) {
|
||||
fluid_log(FLUID_WARN, "sequencer: scale <= 0 : %f\n", scale);
|
||||
|
@ -473,9 +561,13 @@ void fluid_sequencer_set_time_scale(fluid_sequencer_t* seq, double scale)
|
|||
}
|
||||
}
|
||||
|
||||
/** Set the conversion from tick to absolute time (ticks per
|
||||
second). */
|
||||
double fluid_sequencer_get_time_scale(fluid_sequencer_t* seq)
|
||||
/**
|
||||
* Get a sequencer's time scale.
|
||||
* @param seq Sequencer object.
|
||||
* @return Time scale value in ticks per second.
|
||||
*/
|
||||
double
|
||||
fluid_sequencer_get_time_scale(fluid_sequencer_t* seq)
|
||||
{
|
||||
return seq->scale;
|
||||
}
|
||||
|
@ -555,18 +647,11 @@ double fluid_sequencer_get_time_scale(fluid_sequencer_t* seq)
|
|||
*/
|
||||
|
||||
|
||||
|
||||
void _fluid_seq_queue_insert_entry(fluid_sequencer_t* seq, fluid_evt_entry * evtentry);
|
||||
void _fluid_seq_queue_remove_entries_matching(fluid_sequencer_t* seq, fluid_evt_entry* temp);
|
||||
void _fluid_seq_queue_send_queued_events(fluid_sequencer_t* seq);
|
||||
void _fluid_free_evt_queue(fluid_evt_entry** first, fluid_evt_entry** last);
|
||||
|
||||
|
||||
/********************/
|
||||
/* API */
|
||||
/********************/
|
||||
|
||||
short
|
||||
static short
|
||||
_fluid_seq_queue_init(fluid_sequencer_t* seq, int maxEvents)
|
||||
{
|
||||
seq->heap = _fluid_evt_heap_init(maxEvents);
|
||||
|
@ -595,7 +680,7 @@ _fluid_seq_queue_init(fluid_sequencer_t* seq, int maxEvents)
|
|||
return (0);
|
||||
}
|
||||
|
||||
void
|
||||
static void
|
||||
_fluid_seq_queue_end(fluid_sequencer_t* seq)
|
||||
{
|
||||
int i;
|
||||
|
@ -628,10 +713,10 @@ _fluid_seq_queue_end(fluid_sequencer_t* seq)
|
|||
/* queue management */
|
||||
/********************/
|
||||
|
||||
/* create event_entry and append to the preQueue */
|
||||
/* may be called from the main thread (usually) but also recursively
|
||||
from the queue thread, when a callback itself does an insert... */
|
||||
short
|
||||
/* Create event_entry and append to the preQueue.
|
||||
* May be called from the main thread (usually) but also recursively
|
||||
* from the queue thread, when a callback itself does an insert... */
|
||||
static short
|
||||
_fluid_seq_queue_pre_insert(fluid_sequencer_t* seq, fluid_event_t * evt)
|
||||
{
|
||||
fluid_evt_entry * evtentry = _fluid_seq_heap_get_free(seq->heap);
|
||||
|
@ -660,10 +745,10 @@ _fluid_seq_queue_pre_insert(fluid_sequencer_t* seq, fluid_event_t * evt)
|
|||
return (0);
|
||||
}
|
||||
|
||||
/* create event_entry and append to the preQueue */
|
||||
/* may be called from the main thread (usually) but also recursively
|
||||
from the queue thread, when a callback itself does an insert... */
|
||||
void
|
||||
/* Create event_entry and append to the preQueue.
|
||||
* May be called from the main thread (usually) but also recursively
|
||||
* from the queue thread, when a callback itself does an insert... */
|
||||
static void
|
||||
_fluid_seq_queue_pre_remove(fluid_sequencer_t* seq, short src, short dest, int type)
|
||||
{
|
||||
fluid_evt_entry * evtentry = _fluid_seq_heap_get_free(seq->heap);
|
||||
|
@ -697,7 +782,7 @@ _fluid_seq_queue_pre_remove(fluid_sequencer_t* seq, short src, short dest, int t
|
|||
return;
|
||||
}
|
||||
|
||||
void
|
||||
static void
|
||||
_fluid_free_evt_queue(fluid_evt_entry** first, fluid_evt_entry** last)
|
||||
{
|
||||
fluid_evt_entry* tmp2;
|
||||
|
@ -713,12 +798,8 @@ _fluid_free_evt_queue(fluid_evt_entry** first, fluid_evt_entry** last)
|
|||
}
|
||||
}
|
||||
|
||||
/***********************
|
||||
* callback from timer
|
||||
* (may be in a different thread, or in an interrupt)
|
||||
*
|
||||
***********************/
|
||||
int
|
||||
/* Callback from timer (may be in a different thread, or in an interrupt) */
|
||||
static int
|
||||
_fluid_seq_queue_process(void* data, unsigned int msec)
|
||||
{
|
||||
fluid_sequencer_t* seq = (fluid_sequencer_t *)data;
|
||||
|
@ -728,8 +809,9 @@ _fluid_seq_queue_process(void* data, unsigned int msec)
|
|||
}
|
||||
|
||||
/**
|
||||
* Advance sequencer. Do not use if you created the sequencer with useSystemTimer enabled.
|
||||
* @param msec the number of milliseconds (compared to when the sequencer was created).
|
||||
* Advance a sequencer that isn't using the system timer.
|
||||
* @param seq Sequencer object
|
||||
* @param msec Time to advance sequencer to (absolute time since sequencer start).
|
||||
* @since 1.1.0
|
||||
*/
|
||||
void
|
||||
|
@ -768,8 +850,8 @@ fluid_sequencer_process(fluid_sequencer_t* seq, unsigned int msec)
|
|||
|
||||
}
|
||||
|
||||
|
||||
void
|
||||
#if 0
|
||||
static void
|
||||
_fluid_seq_queue_print_later(fluid_sequencer_t* seq)
|
||||
{
|
||||
int count = 0;
|
||||
|
@ -785,9 +867,9 @@ _fluid_seq_queue_print_later(fluid_sequencer_t* seq)
|
|||
}
|
||||
printf("queueLater: Total of %i events\n", count);
|
||||
}
|
||||
#endif
|
||||
|
||||
|
||||
void
|
||||
static void
|
||||
_fluid_seq_queue_insert_queue0(fluid_sequencer_t* seq, fluid_evt_entry* tmp, int cell)
|
||||
{
|
||||
if (seq->queue0[cell][1] == NULL) {
|
||||
|
@ -799,7 +881,7 @@ _fluid_seq_queue_insert_queue0(fluid_sequencer_t* seq, fluid_evt_entry* tmp, int
|
|||
tmp->next = NULL;
|
||||
}
|
||||
|
||||
void
|
||||
static void
|
||||
_fluid_seq_queue_insert_queue1(fluid_sequencer_t* seq, fluid_evt_entry* tmp, int cell)
|
||||
{
|
||||
if (seq->queue1[cell][1] == NULL) {
|
||||
|
@ -811,7 +893,7 @@ _fluid_seq_queue_insert_queue1(fluid_sequencer_t* seq, fluid_evt_entry* tmp, int
|
|||
tmp->next = NULL;
|
||||
}
|
||||
|
||||
void
|
||||
static void
|
||||
_fluid_seq_queue_insert_queue_later(fluid_sequencer_t* seq, fluid_evt_entry* evtentry)
|
||||
{
|
||||
fluid_evt_entry* prev;
|
||||
|
@ -851,7 +933,7 @@ _fluid_seq_queue_insert_queue_later(fluid_sequencer_t* seq, fluid_evt_entry* evt
|
|||
prev->next = evtentry;
|
||||
}
|
||||
|
||||
void
|
||||
static void
|
||||
_fluid_seq_queue_insert_entry(fluid_sequencer_t* seq, fluid_evt_entry * evtentry)
|
||||
{
|
||||
/* time is relative to seq origin, in ticks */
|
||||
|
@ -898,7 +980,7 @@ _fluid_seq_queue_insert_entry(fluid_sequencer_t* seq, fluid_evt_entry * evtentry
|
|||
}
|
||||
}
|
||||
|
||||
int
|
||||
static int
|
||||
_fluid_seq_queue_matchevent(fluid_event_t* evt, int templType, short templSrc, short templDest)
|
||||
{
|
||||
int eventType;
|
||||
|
@ -931,7 +1013,7 @@ _fluid_seq_queue_matchevent(fluid_event_t* evt, int templType, short templSrc, s
|
|||
return 0;
|
||||
}
|
||||
|
||||
void
|
||||
static void
|
||||
_fluid_seq_queue_remove_entries_matching(fluid_sequencer_t* seq, fluid_evt_entry* templ)
|
||||
{
|
||||
/* we walk everything : this is slow, but that is life */
|
||||
|
@ -1032,7 +1114,7 @@ _fluid_seq_queue_remove_entries_matching(fluid_sequencer_t* seq, fluid_evt_entry
|
|||
}
|
||||
}
|
||||
|
||||
void
|
||||
static void
|
||||
_fluid_seq_queue_send_cell_events(fluid_sequencer_t* seq, int cellNb)
|
||||
{
|
||||
fluid_evt_entry* next;
|
||||
|
@ -1051,7 +1133,7 @@ _fluid_seq_queue_send_cell_events(fluid_sequencer_t* seq, int cellNb)
|
|||
seq->queue0[cellNb][1] = NULL;
|
||||
}
|
||||
|
||||
void
|
||||
static void
|
||||
_fluid_seq_queue_slide(fluid_sequencer_t* seq)
|
||||
{
|
||||
short i;
|
||||
|
@ -1108,7 +1190,7 @@ _fluid_seq_queue_slide(fluid_sequencer_t* seq)
|
|||
seq->queueLater = tmp;
|
||||
}
|
||||
|
||||
void
|
||||
static void
|
||||
_fluid_seq_queue_send_queued_events(fluid_sequencer_t* seq)
|
||||
{
|
||||
unsigned int nowTicks = fluid_sequencer_get_tick(seq);
|
||||
|
|
|
@ -49,9 +49,7 @@ typedef struct _fluid_seqbind_t fluid_seqbind_t;
|
|||
int fluid_seqbind_timer_callback(void* data, unsigned int msec);
|
||||
void fluid_seq_fluidsynth_callback(unsigned int time, fluid_event_t* event, fluid_sequencer_t* seq, void* data);
|
||||
|
||||
/**
|
||||
* Proper cleanup of the seqbind struct.
|
||||
*/
|
||||
/* Proper cleanup of the seqbind struct. */
|
||||
void
|
||||
delete_fluid_seqbind(fluid_seqbind_t* seqbind)
|
||||
{
|
||||
|
@ -73,19 +71,21 @@ delete_fluid_seqbind(fluid_seqbind_t* seqbind)
|
|||
}
|
||||
|
||||
/**
|
||||
* Registers fluidsynth as a client of the given sequencer.
|
||||
* The fluidsynth is registered with the name "fluidsynth".
|
||||
* @returns the fluidsynth destID in the sequencer, or -1 if function failed.
|
||||
* Registers a synthesizer as a destination client of the given sequencer.
|
||||
* The \a synth is registered with the name "fluidsynth".
|
||||
* @param seq Sequencer instance
|
||||
* @param synth Synthesizer instance
|
||||
* @returns Sequencer client ID, or #FLUID_FAILED on error.
|
||||
*/
|
||||
short
|
||||
fluid_sequencer_register_fluidsynth(fluid_sequencer_t* seq, fluid_synth_t* synth)
|
||||
fluid_sequencer_register_fluidsynth (fluid_sequencer_t* seq, fluid_synth_t* synth)
|
||||
{
|
||||
fluid_seqbind_t* seqbind;
|
||||
|
||||
seqbind = FLUID_NEW(fluid_seqbind_t);
|
||||
if (seqbind == NULL) {
|
||||
fluid_log(FLUID_PANIC, "sequencer: Out of memory\n");
|
||||
return -1;
|
||||
return FLUID_FAILED;
|
||||
}
|
||||
|
||||
seqbind->synth = synth;
|
||||
|
@ -94,13 +94,13 @@ fluid_sequencer_register_fluidsynth(fluid_sequencer_t* seq, fluid_synth_t* synth
|
|||
seqbind->client_id = -1;
|
||||
|
||||
/* set up the sample timer */
|
||||
if (!fluid_sequencer_get_useSystemTimer(seq)) {
|
||||
if (!fluid_sequencer_get_use_system_timer(seq)) {
|
||||
seqbind->sample_timer =
|
||||
new_fluid_sample_timer(synth, fluid_seqbind_timer_callback, (void *) seqbind);
|
||||
if (seqbind->sample_timer == NULL) {
|
||||
fluid_log(FLUID_PANIC, "sequencer: Out of memory\n");
|
||||
delete_fluid_seqbind(seqbind);
|
||||
return -1;
|
||||
return FLUID_FAILED;
|
||||
}
|
||||
}
|
||||
|
||||
|
@ -109,7 +109,7 @@ fluid_sequencer_register_fluidsynth(fluid_sequencer_t* seq, fluid_synth_t* synth
|
|||
fluid_sequencer_register_client(seq, "fluidsynth", fluid_seq_fluidsynth_callback, (void *)seqbind);
|
||||
if (seqbind->client_id == -1) {
|
||||
delete_fluid_seqbind(seqbind);
|
||||
return -1;
|
||||
return FLUID_FAILED;
|
||||
}
|
||||
|
||||
return seqbind->client_id;
|
||||
|
@ -277,9 +277,9 @@ static int get_fluidsynth_dest(fluid_sequencer_t* seq)
|
|||
/**
|
||||
* Transforms an incoming midi event (from a midi driver or midi router) to a
|
||||
* sequencer event and adds it to the sequencer queue for sending as soon as possible.
|
||||
* @param data the sequencer, must be a valid fluid_sequencer_t
|
||||
* @param event midi event
|
||||
* @return FLUID_OK or FLUID_FAILED
|
||||
* @param data The sequencer, must be a valid #fluid_sequencer_t
|
||||
* @param event MIDI event
|
||||
* @return #FLUID_OK or #FLUID_FAILED
|
||||
* @since 1.1.0
|
||||
*/
|
||||
int
|
||||
|
|
|
@ -699,7 +699,7 @@ fluid_settings_setstr(fluid_settings_t* settings, char* name, char* str)
|
|||
* @param name a setting's name
|
||||
* @param str Caller supplied buffer to copy string value to
|
||||
* @param len Size of 'str' buffer (no more than len bytes will be written, which
|
||||
* will always include a '\0' terminator)
|
||||
* will always include a zero terminator)
|
||||
* @return 1 if the value exists, 0 otherwise
|
||||
* @since 1.1.0
|
||||
*
|
||||
|
|
|
@ -2253,7 +2253,7 @@ fluid_synth_pitch_wheel_sens_LOCAL(fluid_synth_t* synth, int chan, int val)
|
|||
* @param chan MIDI channel number (0 to MIDI channel count - 1)
|
||||
* @param pval Location to store pitch wheel sensitivity value in semitones
|
||||
* @return FLUID_OK on success, FLUID_FAILED otherwise
|
||||
* @since: ?? Seems it was added sometime AFTER v1.0 API freeze.
|
||||
* @since Sometime AFTER v1.0 API freeze.
|
||||
*/
|
||||
int
|
||||
fluid_synth_get_pitch_wheel_sens(fluid_synth_t* synth, int chan, int* pval)
|
||||
|
|
|
@ -186,7 +186,7 @@ fluid_log_config(void)
|
|||
* @param level Log level (#fluid_log_level).
|
||||
* @param fmt Printf style format string for log message
|
||||
* @param ... Arguments for printf 'fmt' message string
|
||||
* @return Always returns -1
|
||||
* @return Always returns #FLUID_FAILED
|
||||
*/
|
||||
int
|
||||
fluid_log(int level, char* fmt, ...)
|
||||
|
@ -286,10 +286,13 @@ fluid_error()
|
|||
return fluid_errbuf;
|
||||
}
|
||||
|
||||
|
||||
/*
|
||||
/**
|
||||
* Check if a file is a MIDI file.
|
||||
* @param filename Path to the file to check
|
||||
* @return TRUE if it could be a MIDI file, FALSE otherwise
|
||||
*
|
||||
* fluid_is_midifile
|
||||
* The current implementation only checks for the "MThd" header in the file.
|
||||
* It is useful only to distinguish between SoundFont and MIDI files.
|
||||
*/
|
||||
int
|
||||
fluid_is_midifile(char* filename)
|
||||
|
@ -309,9 +312,13 @@ fluid_is_midifile(char* filename)
|
|||
return strncmp(id, "MThd", 4) == 0;
|
||||
}
|
||||
|
||||
/*
|
||||
* fluid_is_soundfont
|
||||
/**
|
||||
* Check if a file is a SoundFont file.
|
||||
* @param filename Path to the file to check
|
||||
* @return TRUE if it could be a SoundFont, FALSE otherwise
|
||||
*
|
||||
* The current implementation only checks for the "RIFF" header in the file.
|
||||
* It is useful only to distinguish between SoundFont and MIDI files.
|
||||
*/
|
||||
int
|
||||
fluid_is_soundfont(char* filename)
|
||||
|
|
|
@ -203,19 +203,40 @@ fluid_voice_init(fluid_voice_t* voice, fluid_sample_t* sample,
|
|||
return FLUID_OK;
|
||||
}
|
||||
|
||||
void fluid_voice_gen_set(fluid_voice_t* voice, int i, float val)
|
||||
/**
|
||||
* Set the value of a generator.
|
||||
* @param voice Voice instance
|
||||
* @param i Generator ID (#fluid_gen_type)
|
||||
* @param val Generator value
|
||||
*/
|
||||
void
|
||||
fluid_voice_gen_set(fluid_voice_t* voice, int i, float val)
|
||||
{
|
||||
voice->gen[i].val = val;
|
||||
voice->gen[i].flags = GEN_SET;
|
||||
}
|
||||
|
||||
void fluid_voice_gen_incr(fluid_voice_t* voice, int i, float val)
|
||||
/**
|
||||
* Offset the value of a generator.
|
||||
* @param voice Voice instance
|
||||
* @param i Generator ID (#fluid_gen_type)
|
||||
* @param val Value to add to the existing value
|
||||
*/
|
||||
void
|
||||
fluid_voice_gen_incr(fluid_voice_t* voice, int i, float val)
|
||||
{
|
||||
voice->gen[i].val += val;
|
||||
voice->gen[i].flags = GEN_SET;
|
||||
}
|
||||
|
||||
float fluid_voice_gen_get(fluid_voice_t* voice, int gen)
|
||||
/**
|
||||
* Get the value of a generator.
|
||||
* @param voice Voice instance
|
||||
* @param gen Generator ID (#fluid_gen_type)
|
||||
* @return Current generator value
|
||||
*/
|
||||
float
|
||||
fluid_voice_gen_get(fluid_voice_t* voice, int gen)
|
||||
{
|
||||
return voice->gen[gen].val;
|
||||
}
|
||||
|
@ -1018,10 +1039,6 @@ calculate_hold_decay_buffers(fluid_voice_t* voice, int gen_base,
|
|||
}
|
||||
|
||||
/*
|
||||
* fluid_voice_update_param
|
||||
*
|
||||
* Purpose:
|
||||
*
|
||||
* The value of a generator (gen) has changed. (The different
|
||||
* generators are listed in fluidsynth.h, or in SF2.01 page 48-49)
|
||||
* Now the dependent 'voice' parameters are calculated.
|
||||
|
@ -1036,6 +1053,14 @@ calculate_hold_decay_buffers(fluid_voice_t* voice, int gen_base,
|
|||
* NRPN system. _GEN(voice, generator_enumerator) returns the sum
|
||||
* of all three.
|
||||
*/
|
||||
/**
|
||||
* Update all the synthesis parameters, which depend on generator \a gen.
|
||||
* @param voice Voice instance
|
||||
* @param gen Generator id (#fluid_gen_type)
|
||||
*
|
||||
* This is only necessary after changing a generator of an already operating voice.
|
||||
* Most applications will not need this function.
|
||||
*/
|
||||
void
|
||||
fluid_voice_update_param(fluid_voice_t* voice, int gen)
|
||||
{
|
||||
|
@ -1444,7 +1469,10 @@ fluid_voice_update_param(fluid_voice_t* voice, int gen)
|
|||
}
|
||||
|
||||
/**
|
||||
* fluid_voice_modulate
|
||||
* Recalculate voice parameters for a given control.
|
||||
* @param voice the synthesis voice
|
||||
* @param cc flag to distinguish between a continous control and a channel control (pitch bend, ...)
|
||||
* @param ctrl the control number
|
||||
*
|
||||
* In this implementation, I want to make sure that all controllers
|
||||
* are event based: the parameter values of the DSP algorithm should
|
||||
|
@ -1464,12 +1492,7 @@ fluid_voice_update_param(fluid_voice_t* voice, int gen)
|
|||
*
|
||||
* - For every changed generator, convert its value to the correct
|
||||
* unit of the corresponding DSP parameter
|
||||
*
|
||||
* @fn int fluid_voice_modulate(fluid_voice_t* voice, int cc, int ctrl, int val)
|
||||
* @param voice the synthesis voice
|
||||
* @param cc flag to distinguish between a continous control and a channel control (pitch bend, ...)
|
||||
* @param ctrl the control number
|
||||
* */
|
||||
*/
|
||||
int fluid_voice_modulate(fluid_voice_t* voice, int cc, int ctrl)
|
||||
{
|
||||
int i, k;
|
||||
|
@ -1510,8 +1533,6 @@ int fluid_voice_modulate(fluid_voice_t* voice, int cc, int ctrl)
|
|||
}
|
||||
|
||||
/**
|
||||
* fluid_voice_modulate_all
|
||||
*
|
||||
* Update all the modulators. This function is called after a
|
||||
* ALL_CTRL_OFF MIDI message has been received (CC 121).
|
||||
*
|
||||
|
@ -1670,16 +1691,15 @@ fluid_voice_off(fluid_voice_t* voice)
|
|||
return FLUID_OK;
|
||||
}
|
||||
|
||||
/*
|
||||
* fluid_voice_add_mod
|
||||
*
|
||||
* Adds a modulator to the voice. "mode" indicates, what to do, if
|
||||
* an identical modulator exists already.
|
||||
*
|
||||
* mode == FLUID_VOICE_ADD: Identical modulators on preset level are added
|
||||
* mode == FLUID_VOICE_OVERWRITE: Identical modulators on instrument level are overwritten
|
||||
* mode == FLUID_VOICE_DEFAULT: This is a default modulator, there can be no identical modulator.
|
||||
* Don't check.
|
||||
/**
|
||||
* Adds a modulator to the voice.
|
||||
* @param voice Voice instance
|
||||
* @param mod Modulator info (copied)
|
||||
* @param mode Determines how to handle an existing identical modulator
|
||||
* #FLUID_VOICE_ADD to add (offset) the modulator amounts,
|
||||
* #FLUID_VOICE_OVERWRITE to replace the modulator,
|
||||
* #FLUID_VOICE_DEFAULT when adding a default modulator - no duplicate should
|
||||
* exist so don't check.
|
||||
*/
|
||||
void
|
||||
fluid_voice_add_mod(fluid_voice_t* voice, fluid_mod_t* mod, int mode)
|
||||
|
@ -1735,11 +1755,32 @@ fluid_voice_add_mod(fluid_voice_t* voice, fluid_mod_t* mod, int mode)
|
|||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* Get the unique ID of the noteon-event.
|
||||
* @param voice Voice instance
|
||||
* @return Note on unique ID
|
||||
*
|
||||
* A SoundFont loader may store the voice processes it has created for
|
||||
* real-time control during the operation of a voice (for example: parameter
|
||||
* changes in SoundFont editor). The synth uses a pool of voices, which are
|
||||
* 'recycled' and never deallocated.
|
||||
*
|
||||
* Before modifying an existing voice, check
|
||||
* - that its state is still 'playing'
|
||||
* - that the ID is still the same
|
||||
*
|
||||
* Otherwise the voice has finished playing.
|
||||
*/
|
||||
unsigned int fluid_voice_get_id(fluid_voice_t* voice)
|
||||
{
|
||||
return voice->id;
|
||||
}
|
||||
|
||||
/**
|
||||
* Check if a voice is still playing.
|
||||
* @param voice Voice instance
|
||||
* @return TRUE if playing, FALSE otherwise
|
||||
*/
|
||||
int fluid_voice_is_playing(fluid_voice_t* voice)
|
||||
{
|
||||
return _PLAYING(voice);
|
||||
|
@ -1982,7 +2023,19 @@ int fluid_voice_set_gain(fluid_voice_t* voice, fluid_real_t gain)
|
|||
* - Calculate, what factor will make the loop inaudible
|
||||
* - Store in sample
|
||||
*/
|
||||
int fluid_voice_optimize_sample(fluid_sample_t* s)
|
||||
/**
|
||||
* Calculate the peak volume of a sample for voice off optimization.
|
||||
* @param s Sample to optimize
|
||||
* @return #FLUID_OK on success, #FLUID_FAILED otherwise
|
||||
*
|
||||
* If the peak volume during the loop is known, then the voice can
|
||||
* be released earlier during the release phase. Otherwise, the
|
||||
* voice will operate (inaudibly), until the envelope is at the
|
||||
* nominal turnoff point. So it's a good idea to call
|
||||
* fluid_voice_optimize_sample() on each sample once.
|
||||
*/
|
||||
int
|
||||
fluid_voice_optimize_sample(fluid_sample_t* s)
|
||||
{
|
||||
signed short peak_max = 0;
|
||||
signed short peak_min = 0;
|
||||
|
|
|
@ -154,12 +154,6 @@ typedef double fluid_real_t;
|
|||
#endif
|
||||
|
||||
|
||||
typedef enum {
|
||||
FLUID_OK = 0,
|
||||
FLUID_FAILED = -1
|
||||
} fluid_status;
|
||||
|
||||
|
||||
#if defined(WIN32)
|
||||
typedef SOCKET fluid_socket_t;
|
||||
#else
|
||||
|
|
Loading…
Reference in a new issue