Audio plugin host https://kx.studio/carla
You can not select more than 25 topics Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.

320 lines
14KB

  1. #ifndef __SUNVOX_H__
  2. #define __SUNVOX_H__
  3. #define NOTECMD_NOTE_OFF 128
  4. #define NOTECMD_ALL_NOTES_OFF 129 /* notes of all synths off */
  5. #define NOTECMD_CLEAN_SYNTHS 130 /* stop and clean all synths */
  6. #define NOTECMD_STOP 131
  7. #define NOTECMD_PLAY 132
  8. //sv_send_event() parameters:
  9. // slot;
  10. // channel_num: from 0 to 7;
  11. // note: 0 - nothing; 1..127 - note num; 128 - note off; 129, 130... - see NOTECMD_xxx defines;
  12. // vel: velocity 1..129; 0 - default;
  13. // module: 0 - nothing; 1..255 - module number;
  14. // ctl: CCXX. CC - number of controller. XX - std effect;
  15. // ctl_val: value of controller.
  16. struct sunvox_note
  17. {
  18. unsigned char note; //0 - nothing; 1..127 - note num; 128 - note off; 129, 130... - see NOTECMD_xxx defines
  19. unsigned char vel; //Velocity 1..129; 0 - default
  20. unsigned char module; //0 - nothing; 1..255 - module number
  21. unsigned char nothing;
  22. unsigned short ctl; //CCXX. CC - number of controller. XX - std effect
  23. unsigned short ctl_val; //Value of controller
  24. };
  25. #define SV_INIT_FLAG_NO_DEBUG_OUTPUT ( 1 << 0 )
  26. #define SV_INIT_FLAG_USER_AUDIO_CALLBACK ( 1 << 1 ) /* Interaction with sound card is on the user side */
  27. #define SV_INIT_FLAG_AUDIO_INT16 ( 1 << 2 )
  28. #define SV_INIT_FLAG_AUDIO_FLOAT32 ( 1 << 3 )
  29. #define SV_INIT_FLAG_ONE_THREAD ( 1 << 4 ) /* Audio callback and song modification functions are in single thread */
  30. #define SV_MODULE_FLAG_EXISTS 1
  31. #define SV_MODULE_FLAG_EFFECT 2
  32. #define SV_MODULE_INPUTS_OFF 16
  33. #define SV_MODULE_INPUTS_MASK ( 255 << SV_MODULE_INPUTS_OFF )
  34. #define SV_MODULE_OUTPUTS_OFF ( 16 + 8 )
  35. #define SV_MODULE_OUTPUTS_MASK ( 255 << SV_MODULE_OUTPUTS_OFF )
  36. #define SV_STYPE_INT16 0
  37. #define SV_STYPE_INT32 1
  38. #define SV_STYPE_FLOAT32 2
  39. #define SV_STYPE_FLOAT64 3
  40. #if defined(_WIN32) || defined(_WIN32_WCE) || defined(__WIN32__)
  41. #define WIN
  42. #define LIBNAME "sunvox.dll"
  43. #endif
  44. #if defined(__APPLE__)
  45. #define OSX
  46. #define LIBNAME "sunvox.dylib"
  47. #endif
  48. #if defined(__linux__) || defined(linux)
  49. #define LINUX
  50. #define LIBNAME "./sunvox.so"
  51. #endif
  52. #if defined(OSX) || defined(LINUX)
  53. #define UNIX
  54. #endif
  55. #ifdef WIN
  56. #define SUNVOX_FN_ATTR __attribute__((stdcall))
  57. #endif
  58. #ifndef SUNVOX_FN_ATTR
  59. #define SUNVOX_FN_ATTR /**/
  60. #endif
  61. //sv_audio_callback() - get the next piece of SunVox audio.
  62. //buf - destination buffer of type signed short (if SV_INIT_FLAG_AUDIO_INT16 used in sv_init())
  63. // or float (if SV_INIT_FLAG_AUDIO_FLOAT32 used in sv_init());
  64. // stereo data will be interleaved in this buffer: LRLR... ; where the LR is the one frame;
  65. //frames - number of frames in destination buffer;
  66. //latency - audio latency (in frames);
  67. //out_time - output time (in ticks).
  68. typedef int (*tsv_audio_callback)( void* buf, int frames, int latency, unsigned int out_time ) SUNVOX_FN_ATTR;
  69. typedef int (*tsv_open_slot)( int slot ) SUNVOX_FN_ATTR;
  70. typedef int (*tsv_close_slot)( int slot ) SUNVOX_FN_ATTR;
  71. typedef int (*tsv_lock_slot)( int slot ) SUNVOX_FN_ATTR;
  72. typedef int (*tsv_unlock_slot)( int slot ) SUNVOX_FN_ATTR;
  73. typedef int (*tsv_init)( const char* dev, int freq, int channels, int flags ) SUNVOX_FN_ATTR;
  74. typedef int (*tsv_deinit)( void ) SUNVOX_FN_ATTR;
  75. //sv_get_sample_type() - get internal sample type of the SunVox engine. Return value: one of the SV_STYPE_xxx defines.
  76. //Use it to get the scope buffer type from get_module_scope() function.
  77. typedef int (*tsv_get_sample_type)( void ) SUNVOX_FN_ATTR;
  78. typedef int (*tsv_load)( int slot, const char* name ) SUNVOX_FN_ATTR;
  79. typedef int (*tsv_play)( int slot ) SUNVOX_FN_ATTR;
  80. typedef int (*tsv_play_from_beginning)( int slot ) SUNVOX_FN_ATTR;
  81. typedef int (*tsv_stop)( int slot ) SUNVOX_FN_ATTR;
  82. //autostop values: 0 - disable autostop; 1 - enable autostop.
  83. //When disabled, song is playing infinitely in the loop.
  84. typedef int (*tsv_set_autostop)( int slot, int autostop ) SUNVOX_FN_ATTR;
  85. //sv_end_of_song() return values: 0 - song is playing now; 1 - stopped.
  86. typedef int (*tsv_end_of_song)( int slot ) SUNVOX_FN_ATTR;
  87. typedef int (*tsv_rewind)( int slot, int t ) SUNVOX_FN_ATTR;
  88. typedef int (*tsv_volume)( int slot, int vol ) SUNVOX_FN_ATTR;
  89. typedef int (*tsv_send_event)( int slot, int channel_num, int note, int vel, int module, int ctl, int ctl_val ) SUNVOX_FN_ATTR;
  90. typedef int (*tsv_get_current_line)( int slot ) SUNVOX_FN_ATTR;
  91. typedef int (*tsv_get_current_signal_level)( int slot, int channel ) SUNVOX_FN_ATTR; //From 0 to 255
  92. typedef const char* (*tsv_get_song_name)( int slot ) SUNVOX_FN_ATTR;
  93. typedef int (*tsv_get_song_bpm)( int slot ) SUNVOX_FN_ATTR;
  94. typedef int (*tsv_get_song_tpl)( int slot ) SUNVOX_FN_ATTR;
  95. //Frame is one discrete of the sound. Sampling frequency 44100 Hz means, that you hear 44100 frames per second.
  96. typedef unsigned int (*tsv_get_song_length_frames)( int slot ) SUNVOX_FN_ATTR;
  97. typedef unsigned int (*tsv_get_song_length_lines)( int slot ) SUNVOX_FN_ATTR;
  98. typedef int (*tsv_get_number_of_modules)( int slot ) SUNVOX_FN_ATTR;
  99. typedef int (*tsv_get_module_flags)( int slot, int mod_num ) SUNVOX_FN_ATTR;
  100. typedef int* (*tsv_get_module_inputs)( int slot, int mod_num ) SUNVOX_FN_ATTR;
  101. typedef int* (*tsv_get_module_outputs)( int slot, int mod_num ) SUNVOX_FN_ATTR;
  102. typedef const char* (*tsv_get_module_name)( int slot, int mod_num ) SUNVOX_FN_ATTR;
  103. typedef unsigned int (*tsv_get_module_xy)( int slot, int mod_num ) SUNVOX_FN_ATTR;
  104. typedef int (*tsv_get_module_color)( int slot, int mod_num ) SUNVOX_FN_ATTR;
  105. typedef void* (*tsv_get_module_scope)( int slot, int mod_num, int channel, int* offset, int* buffer_size ) SUNVOX_FN_ATTR;
  106. typedef int (*tsv_get_number_of_patterns)( int slot ) SUNVOX_FN_ATTR;
  107. typedef int (*tsv_get_pattern_x)( int slot, int pat_num ) SUNVOX_FN_ATTR;
  108. typedef int (*tsv_get_pattern_y)( int slot, int pat_num ) SUNVOX_FN_ATTR;
  109. typedef int (*tsv_get_pattern_tracks)( int slot, int pat_num ) SUNVOX_FN_ATTR;
  110. typedef int (*tsv_get_pattern_lines)( int slot, int pat_num ) SUNVOX_FN_ATTR;
  111. typedef sunvox_note* (*tsv_get_pattern_data)( int slot, int pat_num ) SUNVOX_FN_ATTR;
  112. typedef int (*tsv_pattern_mute)( int slot, int pat_num, int mute ) SUNVOX_FN_ATTR; //Use it with sv_lock_slot() and sv_unlock_slot()
  113. //SunVox engine uses its own time space, measured in ticks.
  114. //Use sv_get_ticks() to get current tick counter (from 0 to 0xFFFFFFFF).
  115. //Use sv_get_ticks_per_second() to get the number of SunVox ticks per second.
  116. typedef unsigned int (*tsv_get_ticks)( void ) SUNVOX_FN_ATTR;
  117. typedef unsigned int (*tsv_get_ticks_per_second)( void ) SUNVOX_FN_ATTR;
  118. #ifdef SUNVOX_MAIN
  119. #ifdef WIN
  120. #define IMPORT( Handle, Type, Function, Store ) \
  121. Store = (Type)GetProcAddress( Handle, Function );
  122. #define ERROR_MSG( msg ) MessageBox( 0, TEXT("msg"), TEXT("Error"), MB_OK );
  123. #endif
  124. #ifdef UNIX
  125. #define IMPORT( Handle, Type, Function, Store ) \
  126. Store = (Type)dlsym( Handle, Function );
  127. #define ERROR_MSG( msg ) printf( "ERROR: %s\n", msg );
  128. #endif
  129. tsv_audio_callback sv_audio_callback = 0;
  130. tsv_open_slot sv_open_slot = 0;
  131. tsv_close_slot sv_close_slot = 0;
  132. tsv_lock_slot sv_lock_slot = 0;
  133. tsv_unlock_slot sv_unlock_slot = 0;
  134. tsv_init sv_init = 0;
  135. tsv_deinit sv_deinit = 0;
  136. tsv_get_sample_type sv_get_sample_type = 0;
  137. tsv_load sv_load = 0;
  138. tsv_play sv_play = 0;
  139. tsv_play_from_beginning sv_play_from_beginning = 0;
  140. tsv_stop sv_stop = 0;
  141. tsv_set_autostop sv_set_autostop = 0;
  142. tsv_end_of_song sv_end_of_song = 0;
  143. tsv_rewind sv_rewind = 0;
  144. tsv_volume sv_volume = 0;
  145. tsv_send_event sv_send_event = 0;
  146. tsv_get_current_line sv_get_current_line = 0;
  147. tsv_get_current_signal_level sv_get_current_signal_level = 0;
  148. tsv_get_song_name sv_get_song_name = 0;
  149. tsv_get_song_bpm sv_get_song_bpm = 0;
  150. tsv_get_song_tpl sv_get_song_tpl = 0;
  151. tsv_get_song_length_frames sv_get_song_length_frames = 0;
  152. tsv_get_song_length_lines sv_get_song_length_lines = 0;
  153. tsv_get_number_of_modules sv_get_number_of_modules = 0;
  154. tsv_get_module_flags sv_get_module_flags = 0;
  155. tsv_get_module_inputs sv_get_module_inputs = 0;
  156. tsv_get_module_outputs sv_get_module_outputs = 0;
  157. tsv_get_module_name sv_get_module_name = 0;
  158. tsv_get_module_xy sv_get_module_xy = 0;
  159. tsv_get_module_color sv_get_module_color = 0;
  160. tsv_get_module_scope sv_get_module_scope = 0;
  161. tsv_get_number_of_patterns sv_get_number_of_patterns = 0;
  162. tsv_get_pattern_x sv_get_pattern_x = 0;
  163. tsv_get_pattern_y sv_get_pattern_y = 0;
  164. tsv_get_pattern_tracks sv_get_pattern_tracks = 0;
  165. tsv_get_pattern_lines sv_get_pattern_lines = 0;
  166. tsv_get_pattern_data sv_get_pattern_data = 0;
  167. tsv_pattern_mute sv_pattern_mute = 0;
  168. tsv_get_ticks sv_get_ticks = 0;
  169. tsv_get_ticks_per_second sv_get_ticks_per_second = 0;
  170. #ifdef UNIX
  171. void* g_sv_dll = 0;
  172. #endif
  173. #ifdef WIN
  174. HMODULE g_sv_dll = 0;
  175. #endif
  176. int sv_load_dll( void )
  177. {
  178. #ifdef WIN
  179. g_sv_dll = LoadLibrary( TEXT(LIBNAME) );
  180. if( g_sv_dll == 0 )
  181. {
  182. ERROR_MSG( "sunvox.dll not found" );
  183. return 1;
  184. }
  185. #endif
  186. #ifdef UNIX
  187. g_sv_dll = dlopen( LIBNAME, RTLD_NOW );
  188. if( g_sv_dll == 0 )
  189. {
  190. printf( "%s\n", dlerror() );
  191. return 1;
  192. }
  193. #endif
  194. IMPORT( g_sv_dll, tsv_audio_callback, "sv_audio_callback", sv_audio_callback );
  195. IMPORT( g_sv_dll, tsv_open_slot, "sv_open_slot", sv_open_slot );
  196. IMPORT( g_sv_dll, tsv_close_slot, "sv_close_slot", sv_close_slot );
  197. IMPORT( g_sv_dll, tsv_lock_slot, "sv_lock_slot", sv_lock_slot );
  198. IMPORT( g_sv_dll, tsv_unlock_slot, "sv_unlock_slot", sv_unlock_slot );
  199. IMPORT( g_sv_dll, tsv_init, "sv_init", sv_init );
  200. IMPORT( g_sv_dll, tsv_deinit, "sv_deinit", sv_deinit );
  201. IMPORT( g_sv_dll, tsv_get_sample_type, "sv_get_sample_type", sv_get_sample_type );
  202. IMPORT( g_sv_dll, tsv_load, "sv_load", sv_load );
  203. IMPORT( g_sv_dll, tsv_play, "sv_play", sv_play );
  204. IMPORT( g_sv_dll, tsv_play_from_beginning, "sv_play_from_beginning", sv_play_from_beginning );
  205. IMPORT( g_sv_dll, tsv_stop, "sv_stop", sv_stop );
  206. IMPORT( g_sv_dll, tsv_set_autostop, "sv_set_autostop", sv_set_autostop );
  207. IMPORT( g_sv_dll, tsv_end_of_song, "sv_end_of_song", sv_end_of_song );
  208. IMPORT( g_sv_dll, tsv_rewind, "sv_rewind", sv_rewind );
  209. IMPORT( g_sv_dll, tsv_volume, "sv_volume", sv_volume );
  210. IMPORT( g_sv_dll, tsv_send_event, "sv_send_event", sv_send_event );
  211. IMPORT( g_sv_dll, tsv_get_current_line, "sv_get_current_line", sv_get_current_line );
  212. IMPORT( g_sv_dll, tsv_get_current_signal_level, "sv_get_current_signal_level", sv_get_current_signal_level );
  213. IMPORT( g_sv_dll, tsv_get_song_name, "sv_get_song_name", sv_get_song_name );
  214. IMPORT( g_sv_dll, tsv_get_song_bpm, "sv_get_song_bpm", sv_get_song_bpm );
  215. IMPORT( g_sv_dll, tsv_get_song_tpl, "sv_get_song_tpl", sv_get_song_tpl );
  216. IMPORT( g_sv_dll, tsv_get_song_length_frames, "sv_get_song_length_frames", sv_get_song_length_frames );
  217. IMPORT( g_sv_dll, tsv_get_song_length_lines, "sv_get_song_length_lines", sv_get_song_length_lines );
  218. IMPORT( g_sv_dll, tsv_get_number_of_modules, "sv_get_number_of_modules", sv_get_number_of_modules );
  219. IMPORT( g_sv_dll, tsv_get_module_flags, "sv_get_module_flags", sv_get_module_flags );
  220. IMPORT( g_sv_dll, tsv_get_module_inputs, "sv_get_module_inputs", sv_get_module_inputs );
  221. IMPORT( g_sv_dll, tsv_get_module_outputs, "sv_get_module_outputs", sv_get_module_outputs );
  222. IMPORT( g_sv_dll, tsv_get_module_name, "sv_get_module_name", sv_get_module_name );
  223. IMPORT( g_sv_dll, tsv_get_module_xy, "sv_get_module_xy", sv_get_module_xy );
  224. IMPORT( g_sv_dll, tsv_get_module_color, "sv_get_module_color", sv_get_module_color );
  225. IMPORT( g_sv_dll, tsv_get_module_scope, "sv_get_module_scope", sv_get_module_scope );
  226. IMPORT( g_sv_dll, tsv_get_number_of_patterns, "sv_get_number_of_patterns", sv_get_number_of_patterns );
  227. IMPORT( g_sv_dll, tsv_get_pattern_x, "sv_get_pattern_x", sv_get_pattern_x );
  228. IMPORT( g_sv_dll, tsv_get_pattern_y, "sv_get_pattern_y", sv_get_pattern_y );
  229. IMPORT( g_sv_dll, tsv_get_pattern_tracks, "sv_get_pattern_tracks", sv_get_pattern_tracks );
  230. IMPORT( g_sv_dll, tsv_get_pattern_lines, "sv_get_pattern_lines", sv_get_pattern_lines );
  231. IMPORT( g_sv_dll, tsv_get_pattern_data, "sv_get_pattern_data", sv_get_pattern_data );
  232. IMPORT( g_sv_dll, tsv_pattern_mute, "sv_pattern_mute", sv_pattern_mute );
  233. IMPORT( g_sv_dll, tsv_get_ticks, "sv_get_ticks", sv_get_ticks );
  234. IMPORT( g_sv_dll, tsv_get_ticks_per_second, "sv_get_ticks_per_second", sv_get_ticks_per_second );
  235. int nf = 0;
  236. while( 1 )
  237. {
  238. if( sv_audio_callback == 0 ) break; nf++;
  239. if( sv_open_slot == 0 ) break; nf++;
  240. if( sv_close_slot == 0 ) break; nf++;
  241. if( sv_lock_slot == 0 ) break; nf++;
  242. if( sv_unlock_slot == 0 ) break; nf++;
  243. if( sv_init == 0 ) break; nf++;
  244. if( sv_deinit == 0 ) break; nf++;
  245. if( sv_get_sample_type == 0 ) break; nf++;
  246. if( sv_load == 0 ) break; nf++;
  247. if( sv_play == 0 ) break; nf++;
  248. if( sv_play_from_beginning == 0 ) break; nf++;
  249. if( sv_stop == 0 ) break; nf++;
  250. if( sv_set_autostop == 0 ) break; nf++;
  251. if( sv_end_of_song == 0 ) break; nf++;
  252. if( sv_rewind == 0 ) break; nf++;
  253. if( sv_volume == 0 ) break; nf++;
  254. if( sv_send_event == 0 ) break; nf++;
  255. if( sv_get_song_name == 0 ) break; nf++;
  256. if( sv_get_song_bpm == 0 ) break; nf++;
  257. if( sv_get_song_tpl == 0 ) break; nf++;
  258. if( sv_get_song_length_frames == 0 ) break; nf++;
  259. if( sv_get_song_length_lines == 0 ) break; nf++;
  260. if( sv_get_number_of_modules == 0 ) break; nf++;
  261. if( sv_get_module_flags == 0 ) break; nf++;
  262. if( sv_get_module_inputs == 0 ) break; nf++;
  263. if( sv_get_module_outputs == 0 ) break; nf++;
  264. if( sv_get_module_name == 0 ) break; nf++;
  265. if( sv_get_module_xy == 0 ) break; nf++;
  266. if( sv_get_module_color == 0 ) break; nf++;
  267. if( sv_get_module_scope == 0 ) break; nf++;
  268. if( sv_get_number_of_patterns == 0 ) break; nf++;
  269. if( sv_get_pattern_x == 0 ) break; nf++;
  270. if( sv_get_pattern_y == 0 ) break; nf++;
  271. if( sv_get_pattern_tracks == 0 ) break; nf++;
  272. if( sv_get_pattern_lines == 0 ) break; nf++;
  273. if( sv_get_pattern_data == 0 ) break; nf++;
  274. if( sv_pattern_mute == 0 ) break; nf++;
  275. if( sv_get_current_line == 0 ) break; nf++;
  276. if( sv_get_current_signal_level == 0 ) break; nf++;
  277. if( sv_get_ticks == 0 ) break; nf++;
  278. if( sv_get_ticks_per_second == 0 ) break; nf++;
  279. nf = 0;
  280. break;
  281. }
  282. if( nf )
  283. {
  284. char ts[ 256 ];
  285. sprintf( ts, "sunvox lib: some functions not found (%d)", nf );
  286. ERROR_MSG( ts );
  287. return nf;
  288. }
  289. return 0;
  290. }
  291. int sv_unload_dll( void )
  292. {
  293. #ifdef UNIX
  294. if( g_sv_dll ) dlclose( g_sv_dll );
  295. #endif
  296. return 0;
  297. }
  298. #endif
  299. #endif