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.

261 lines
7.2KB

  1. /* Audio Library for Teensy 3.X
  2. * Copyright (c) 2014, Paul Stoffregen, paul@pjrc.com
  3. *
  4. * Development of this audio library was funded by PJRC.COM, LLC by sales of
  5. * Teensy and Audio Adaptor boards. Please support PJRC's efforts to develop
  6. * open source software by purchasing Teensy or other PJRC products.
  7. *
  8. * Permission is hereby granted, free of charge, to any person obtaining a copy
  9. * of this software and associated documentation files (the "Software"), to deal
  10. * in the Software without restriction, including without limitation the rights
  11. * to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
  12. * copies of the Software, and to permit persons to whom the Software is
  13. * furnished to do so, subject to the following conditions:
  14. *
  15. * The above copyright notice, development funding notice, and this permission
  16. * notice shall be included in all copies or substantial portions of the Software.
  17. *
  18. * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
  19. * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
  20. * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
  21. * AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
  22. * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
  23. * OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
  24. * THE SOFTWARE.
  25. */
  26. #ifndef synth_waveform_h_
  27. #define synth_waveform_h_
  28. #include <Arduino.h>
  29. #include "AudioStream.h"
  30. #include "arm_math.h"
  31. // waveforms.c
  32. extern "C" {
  33. extern const int16_t AudioWaveformSine[257];
  34. }
  35. #define WAVEFORM_SINE 0
  36. #define WAVEFORM_SAWTOOTH 1
  37. #define WAVEFORM_SQUARE 2
  38. #define WAVEFORM_TRIANGLE 3
  39. #define WAVEFORM_ARBITRARY 4
  40. #define WAVEFORM_PULSE 5
  41. #define WAVEFORM_SAWTOOTH_REVERSE 6
  42. #define WAVEFORM_SAMPLE_HOLD 7
  43. #define WAVEFORM_TRIANGLE_VARIABLE 8
  44. #define WAVEFORM_BANDLIMIT_SAWTOOTH 9
  45. #define WAVEFORM_BANDLIMIT_SAWTOOTH_REVERSE 10
  46. #define WAVEFORM_BANDLIMIT_SQUARE 11
  47. typedef struct step_state
  48. {
  49. int offset ;
  50. bool positive ;
  51. } step_state ;
  52. class BandLimitedWaveform
  53. {
  54. public:
  55. BandLimitedWaveform (void) ;
  56. int16_t generate_sawtooth (uint32_t new_phase, int i) ;
  57. int16_t generate_square (uint32_t new_phase, int i) ;
  58. void init_sawtooth (uint32_t freq_word) ;
  59. void init_square (uint32_t freq_word) ;
  60. private:
  61. int32_t lookup (int offset) ;
  62. void insert_step (int offset, bool rising, int i) ;
  63. int32_t process_step (int i) ;
  64. int32_t process_active_steps (uint32_t new_phase) ;
  65. int32_t process_active_steps_saw (uint32_t new_phase) ;
  66. void new_step_check (uint32_t new_phase, int i) ;
  67. void new_step_check_saw (uint32_t new_phase, int i) ;
  68. uint32_t phase_word ;
  69. int32_t dc_offset ;
  70. step_state states [32] ; // circular buffer of active steps
  71. int newptr ; // buffer pointers into states, AND'd with PTRMASK to keep in buffer range.
  72. int delptr ;
  73. int16_t cyclic[16] ; // circular buffer of output samples
  74. };
  75. class AudioSynthWaveform : public AudioStream
  76. {
  77. public:
  78. AudioSynthWaveform(void) : AudioStream(0,NULL),
  79. phase_accumulator(0), phase_increment(0), phase_offset(0),
  80. magnitude(0), pulse_width(0x40000000),
  81. arbdata(NULL), sample(0), tone_type(WAVEFORM_SINE),
  82. tone_offset(0) {
  83. }
  84. void frequency(float freq) {
  85. if (freq < 0.0) {
  86. freq = 0.0;
  87. } else if (freq > AUDIO_SAMPLE_RATE_EXACT / 2) {
  88. freq = AUDIO_SAMPLE_RATE_EXACT / 2;
  89. }
  90. phase_increment = freq * (4294967296.0 / AUDIO_SAMPLE_RATE_EXACT);
  91. if (phase_increment > 0x7FFE0000u) phase_increment = 0x7FFE0000;
  92. }
  93. void phase(float angle) {
  94. if (angle < 0.0) {
  95. angle = 0.0;
  96. } else if (angle > 360.0) {
  97. angle = angle - 360.0;
  98. if (angle >= 360.0) return;
  99. }
  100. phase_offset = angle * (4294967296.0 / 360.0);
  101. }
  102. void amplitude(float n) { // 0 to 1.0
  103. if (n < 0) {
  104. n = 0;
  105. } else if (n > 1.0) {
  106. n = 1.0;
  107. }
  108. magnitude = n * 65536.0;
  109. }
  110. void offset(float n) {
  111. if (n < -1.0) {
  112. n = -1.0;
  113. } else if (n > 1.0) {
  114. n = 1.0;
  115. }
  116. tone_offset = n * 32767.0;
  117. }
  118. void pulseWidth(float n) { // 0.0 to 1.0
  119. if (n < 0) {
  120. n = 0;
  121. } else if (n > 1.0) {
  122. n = 1.0;
  123. }
  124. pulse_width = n * 4294967296.0;
  125. }
  126. void begin(short t_type) {
  127. phase_offset = 0;
  128. tone_type = t_type;
  129. if (t_type == WAVEFORM_BANDLIMIT_SQUARE)
  130. band_limit_waveform.init_square (phase_increment) ;
  131. if (t_type == WAVEFORM_BANDLIMIT_SAWTOOTH || t_type == WAVEFORM_BANDLIMIT_SAWTOOTH_REVERSE)
  132. band_limit_waveform.init_sawtooth (phase_increment) ;
  133. }
  134. void begin(float t_amp, float t_freq, short t_type) {
  135. amplitude(t_amp);
  136. frequency(t_freq);
  137. phase_offset = 0;
  138. begin (t_type);
  139. }
  140. void arbitraryWaveform(const int16_t *data, float maxFreq) {
  141. arbdata = data;
  142. }
  143. virtual void update(void);
  144. private:
  145. uint32_t phase_accumulator;
  146. uint32_t phase_increment;
  147. uint32_t phase_offset;
  148. int32_t magnitude;
  149. uint32_t pulse_width;
  150. const int16_t *arbdata;
  151. int16_t sample; // for WAVEFORM_SAMPLE_HOLD
  152. short tone_type;
  153. int16_t tone_offset;
  154. BandLimitedWaveform band_limit_waveform ;
  155. };
  156. class AudioSynthWaveformModulated : public AudioStream
  157. {
  158. public:
  159. AudioSynthWaveformModulated(void) : AudioStream(2, inputQueueArray),
  160. phase_accumulator(0), phase_increment(0), modulation_factor(32768),
  161. magnitude(0), arbdata(NULL), sample(0), tone_offset(0),
  162. tone_type(WAVEFORM_SINE), modulation_type(0) {
  163. }
  164. void frequency(float freq) {
  165. if (freq < 0.0) {
  166. freq = 0.0;
  167. } else if (freq > AUDIO_SAMPLE_RATE_EXACT / 2) {
  168. freq = AUDIO_SAMPLE_RATE_EXACT / 2;
  169. }
  170. phase_increment = freq * (4294967296.0 / AUDIO_SAMPLE_RATE_EXACT);
  171. if (phase_increment > 0x7FFE0000u) phase_increment = 0x7FFE0000;
  172. }
  173. void amplitude(float n) { // 0 to 1.0
  174. if (n < 0) {
  175. n = 0;
  176. } else if (n > 1.0) {
  177. n = 1.0;
  178. }
  179. magnitude = n * 65536.0;
  180. }
  181. void offset(float n) {
  182. if (n < -1.0) {
  183. n = -1.0;
  184. } else if (n > 1.0) {
  185. n = 1.0;
  186. }
  187. tone_offset = n * 32767.0;
  188. }
  189. void begin(short t_type) {
  190. tone_type = t_type;
  191. if (t_type == WAVEFORM_BANDLIMIT_SQUARE)
  192. band_limit_waveform.init_square (phase_increment) ;
  193. if (t_type == WAVEFORM_BANDLIMIT_SAWTOOTH || t_type == WAVEFORM_BANDLIMIT_SAWTOOTH_REVERSE)
  194. band_limit_waveform.init_sawtooth (phase_increment) ;
  195. }
  196. void begin(float t_amp, float t_freq, short t_type) {
  197. amplitude(t_amp);
  198. frequency(t_freq);
  199. begin (t_type) ;
  200. }
  201. void arbitraryWaveform(const int16_t *data, float maxFreq) {
  202. arbdata = data;
  203. }
  204. void frequencyModulation(float octaves) {
  205. if (octaves > 12.0) {
  206. octaves = 12.0;
  207. } else if (octaves < 0.1) {
  208. octaves = 0.1;
  209. }
  210. modulation_factor = octaves * 4096.0;
  211. modulation_type = 0;
  212. }
  213. void phaseModulation(float degrees) {
  214. if (degrees > 9000.0) {
  215. degrees = 9000.0;
  216. } else if (degrees < 30.0) {
  217. degrees = 30.0;
  218. }
  219. modulation_factor = degrees * (65536.0 / 180.0);
  220. modulation_type = 1;
  221. }
  222. virtual void update(void);
  223. private:
  224. audio_block_t *inputQueueArray[2];
  225. uint32_t phase_accumulator;
  226. uint32_t phase_increment;
  227. uint32_t modulation_factor;
  228. int32_t magnitude;
  229. const int16_t *arbdata;
  230. uint32_t phasedata[AUDIO_BLOCK_SAMPLES];
  231. int16_t sample; // for WAVEFORM_SAMPLE_HOLD
  232. int16_t tone_offset;
  233. uint8_t tone_type;
  234. uint8_t modulation_type;
  235. BandLimitedWaveform band_limit_waveform ;
  236. };
  237. #endif