first commit synth design tool guide code
This commit is contained in:
parent
3f5f52108c
commit
7c03d5d051
3 changed files with 388 additions and 0 deletions
|
|
@ -0,0 +1,190 @@
|
||||||
|
/* Audio library demonstration - pocket synth with C major scale and 4 wave types */
|
||||||
|
//each row is a different waveform, envelope, and effect set in major scale
|
||||||
|
// row 0 sine, soft attack, long release ADSR
|
||||||
|
// row 1 square, hard attack, moderate release, flanger effect
|
||||||
|
// row 2 sawtooth, hard attack, soft release, chorus effect
|
||||||
|
// row 3 triangle, medium attack, long release ADSR, multi tap delay
|
||||||
|
|
||||||
|
#include <Audio.h>
|
||||||
|
#include <Adafruit_NeoTrellisM4.h>
|
||||||
|
|
||||||
|
Adafruit_NeoTrellisM4 trellis = Adafruit_NeoTrellisM4();
|
||||||
|
// Paste your Audio System Design Tool code below this line:
|
||||||
|
// GUItool: begin automatically generated code
|
||||||
|
AudioSynthWaveform wave0; //xy=453.84613037109375,254.61540985107422
|
||||||
|
AudioSynthWaveform wave1; //xy=453.84613037109375,294.6154098510742
|
||||||
|
AudioSynthWaveform wave2; //xy=453.84613037109375,354.6154098510742
|
||||||
|
AudioSynthWaveform wave3; //xy=453.84613037109375,404.6154098510742
|
||||||
|
AudioEffectEnvelope env0; //xy=602.8461303710938,254.61540985107422
|
||||||
|
AudioEffectEnvelope env1; //xy=602.8461303710938,294.6154098510742
|
||||||
|
AudioEffectEnvelope env2; //xy=602.8461303710938,354.6154098510742
|
||||||
|
AudioEffectEnvelope env3; //xy=602.8461303710938,404.6154098510742
|
||||||
|
AudioEffectChorus chorus1; //xy=734.6796264648438,333.14093017578125
|
||||||
|
AudioEffectFlange flange1; //xy=737.7564392089844,284.6794891357422
|
||||||
|
AudioEffectDelay delay1; //xy=880.7692260742188,582.3077392578125
|
||||||
|
AudioMixer4 mixer1; //xy=882.3076171875,284.6154327392578
|
||||||
|
AudioMixer4 mixerLeft; //xy=1041.9999389648438,293.84617614746094
|
||||||
|
AudioMixer4 mixerRight; //xy=1045.0768432617188,394.6153869628906
|
||||||
|
AudioOutputAnalogStereo audioOut; //xy=1212.8461303710938,354.6154098510742
|
||||||
|
AudioConnection patchCord1(wave0, env0);
|
||||||
|
AudioConnection patchCord2(wave1, env1);
|
||||||
|
AudioConnection patchCord3(wave2, env2);
|
||||||
|
AudioConnection patchCord4(wave3, env3);
|
||||||
|
AudioConnection patchCord5(env0, 0, mixer1, 0);
|
||||||
|
AudioConnection patchCord6(env1, flange1);
|
||||||
|
AudioConnection patchCord7(env2, chorus1);
|
||||||
|
AudioConnection patchCord8(env3, delay1);
|
||||||
|
AudioConnection patchCord9(env3, 0, mixer1, 3);
|
||||||
|
AudioConnection patchCord10(chorus1, 0, mixer1, 2);
|
||||||
|
AudioConnection patchCord11(flange1, 0, mixer1, 1);
|
||||||
|
AudioConnection patchCord12(delay1, 0, mixerLeft, 1);
|
||||||
|
AudioConnection patchCord13(delay1, 1, mixerLeft, 2);
|
||||||
|
AudioConnection patchCord14(delay1, 2, mixerRight, 1);
|
||||||
|
AudioConnection patchCord15(delay1, 3, mixerRight, 2);
|
||||||
|
AudioConnection patchCord16(mixer1, 0, mixerLeft, 0);
|
||||||
|
AudioConnection patchCord17(mixer1, 0, mixerRight, 0);
|
||||||
|
AudioConnection patchCord18(mixerLeft, 0, audioOut, 0);
|
||||||
|
AudioConnection patchCord19(mixerRight, 0, audioOut, 1);
|
||||||
|
// GUItool: end automatically generated code
|
||||||
|
|
||||||
|
AudioSynthWaveform *waves[4] = {
|
||||||
|
&wave0, &wave1, &wave2, &wave3,
|
||||||
|
};
|
||||||
|
short wave_type[4] = {
|
||||||
|
WAVEFORM_SINE,
|
||||||
|
WAVEFORM_SQUARE,
|
||||||
|
WAVEFORM_SAWTOOTH,
|
||||||
|
WAVEFORM_TRIANGLE,
|
||||||
|
};
|
||||||
|
float cmaj_low[8] = { 130.81, 146.83, 164.81, 174.61, 196.00, 220.00, 246.94, 261.63 };
|
||||||
|
float cmaj_high[8] = { 261.6, 293.7, 329.6, 349.2, 392.0, 440.0, 493.9, 523.3 };
|
||||||
|
AudioEffectEnvelope *envs[4] = {
|
||||||
|
&env0, &env1, &env2, &env3,
|
||||||
|
};
|
||||||
|
int n_chorus = 5;
|
||||||
|
#define CHORUS_DELAY_LENGTH (400*AUDIO_BLOCK_SAMPLES)
|
||||||
|
short chorusDelayline[CHORUS_DELAY_LENGTH];
|
||||||
|
|
||||||
|
#define FLANGER_DELAY_LENGTH (6*AUDIO_BLOCK_SAMPLES)
|
||||||
|
short flangerDelayline[FLANGER_DELAY_LENGTH];
|
||||||
|
|
||||||
|
void setup(){
|
||||||
|
Serial.begin(115200);
|
||||||
|
//while (!Serial);
|
||||||
|
|
||||||
|
trellis.begin();
|
||||||
|
trellis.setBrightness(255);
|
||||||
|
|
||||||
|
AudioMemory(120);
|
||||||
|
|
||||||
|
//Initialize the waveform nodes
|
||||||
|
wave0.begin(0.85, 50, WAVEFORM_SINE);
|
||||||
|
wave1.begin(0.4, 50, WAVEFORM_SQUARE);
|
||||||
|
wave2.begin(0.6, 50, WAVEFORM_SAWTOOTH);
|
||||||
|
wave3.begin(0.4, 50, WAVEFORM_TRIANGLE);
|
||||||
|
|
||||||
|
// reduce the gain on some channels, so half of the channels
|
||||||
|
// are "positioned" to the left, half to the right, but all
|
||||||
|
// are heard at least partially on both ears
|
||||||
|
mixerLeft.gain(0, 0.3);
|
||||||
|
mixerLeft.gain(1, 0.1);
|
||||||
|
mixerLeft.gain(2, 0.5);
|
||||||
|
|
||||||
|
mixerRight.gain(0, 0.3);
|
||||||
|
mixerRight.gain(1, 0.5);
|
||||||
|
mixerRight.gain(2, 0.1);
|
||||||
|
|
||||||
|
|
||||||
|
// set envelope parameters, for pleasing sound :-)
|
||||||
|
env0.attack(300);
|
||||||
|
env0.hold(2);
|
||||||
|
env0.decay(30);
|
||||||
|
env0.sustain(0.6);
|
||||||
|
env0.release(1200);
|
||||||
|
|
||||||
|
env1.attack(10);
|
||||||
|
env1.hold(2);
|
||||||
|
env1.decay(30);
|
||||||
|
env1.sustain(0.6);
|
||||||
|
env1.release(400);
|
||||||
|
|
||||||
|
env2.attack(10);
|
||||||
|
env2.hold(20);
|
||||||
|
env2.decay(30);
|
||||||
|
env2.sustain(0.6);
|
||||||
|
env2.release(1000);
|
||||||
|
|
||||||
|
env3.attack(10);
|
||||||
|
env3.hold(2);
|
||||||
|
env3.decay(30);
|
||||||
|
env3.sustain(0.6);
|
||||||
|
env3.release(600);
|
||||||
|
|
||||||
|
// set delay parameters
|
||||||
|
delay1.delay(0, 110);
|
||||||
|
delay1.delay(1, 660);
|
||||||
|
delay1.delay(2, 220);
|
||||||
|
delay1.delay(3, 1220);
|
||||||
|
|
||||||
|
// set effects parameters
|
||||||
|
chorus1.begin(chorusDelayline, CHORUS_DELAY_LENGTH, n_chorus);
|
||||||
|
flange1.begin(flangerDelayline, FLANGER_DELAY_LENGTH, FLANGER_DELAY_LENGTH/4, FLANGER_DELAY_LENGTH/4, .5);
|
||||||
|
|
||||||
|
|
||||||
|
Serial.println("setup done");
|
||||||
|
|
||||||
|
// Initialize processor and memory measurements
|
||||||
|
AudioProcessorUsageMaxReset();
|
||||||
|
AudioMemoryUsageMaxReset();
|
||||||
|
}
|
||||||
|
|
||||||
|
void noteOn(int num){
|
||||||
|
int voice = num/8;
|
||||||
|
float *scale;
|
||||||
|
if(voice == 0 || voice == 1) scale = cmaj_low;
|
||||||
|
else scale = cmaj_high;
|
||||||
|
AudioNoInterrupts();
|
||||||
|
waves[voice]->frequency(scale[num%8]);
|
||||||
|
envs[voice]->noteOn();
|
||||||
|
AudioInterrupts();
|
||||||
|
}
|
||||||
|
|
||||||
|
void noteOff(int num){
|
||||||
|
int voice = num/8;
|
||||||
|
envs[voice]->noteOff();
|
||||||
|
}
|
||||||
|
|
||||||
|
void loop() {
|
||||||
|
trellis.tick();
|
||||||
|
|
||||||
|
while(trellis.available())
|
||||||
|
{
|
||||||
|
keypadEvent e = trellis.read();
|
||||||
|
int keyindex = e.bit.KEY;
|
||||||
|
if(e.bit.EVENT == KEY_JUST_PRESSED){
|
||||||
|
trellis.setPixelColor(keyindex, Wheel(keyindex * 255 / 32)); // rainbow!
|
||||||
|
noteOn(keyindex);
|
||||||
|
}
|
||||||
|
else if(e.bit.EVENT == KEY_JUST_RELEASED){
|
||||||
|
noteOff(keyindex);
|
||||||
|
trellis.setPixelColor(keyindex, 0);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
delay(10);
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
// Input a value 0 to 255 to get a color value.
|
||||||
|
// The colours are a transition r - g - b - back to r.
|
||||||
|
uint32_t Wheel(byte WheelPos) {
|
||||||
|
WheelPos = 255 - WheelPos;
|
||||||
|
if(WheelPos < 85) {
|
||||||
|
return Adafruit_NeoPixel::Color(255 - WheelPos * 3, 0, WheelPos * 3);
|
||||||
|
}
|
||||||
|
if(WheelPos < 170) {
|
||||||
|
WheelPos -= 85;
|
||||||
|
return Adafruit_NeoPixel::Color(0, WheelPos * 3, 255 - WheelPos * 3);
|
||||||
|
}
|
||||||
|
WheelPos -= 170;
|
||||||
|
return Adafruit_NeoPixel::Color(WheelPos * 3, 255 - WheelPos * 3, 0);
|
||||||
|
}
|
||||||
|
|
@ -0,0 +1,52 @@
|
||||||
|
/*
|
||||||
|
Audio Library on Trellis M4
|
||||||
|
Demo of the audio sweep function.
|
||||||
|
The user specifies the amplitude,
|
||||||
|
start and end frequencies (which can sweep up or down)
|
||||||
|
and the length of time of the sweep.
|
||||||
|
*/
|
||||||
|
|
||||||
|
#include <Audio.h>
|
||||||
|
// Paste your Audio System Design Tool code below this line:
|
||||||
|
// GUItool: begin automatically generated code
|
||||||
|
AudioSynthToneSweep tonesweep1; //xy=531.0833129882812,166.08334350585938
|
||||||
|
AudioOutputAnalogStereo audioOutput; //xy=727.0833129882812,166.08334350585938
|
||||||
|
AudioConnection patchCord1(tonesweep1, 0, audioOutput, 0);
|
||||||
|
AudioConnection patchCord2(tonesweep1, 0, audioOutput, 1);
|
||||||
|
// GUItool: end automatically generated code
|
||||||
|
|
||||||
|
float t_ampx = 0.05; // Amplitude
|
||||||
|
int t_lox = 10; // Low frequency
|
||||||
|
int t_hix = 22000; // High frequency
|
||||||
|
float t_timex = 10; // Length of time of the sweep in seconds
|
||||||
|
|
||||||
|
|
||||||
|
void setup(void) {
|
||||||
|
|
||||||
|
Serial.begin(9600);
|
||||||
|
//while (!Serial) ;
|
||||||
|
delay(3000);
|
||||||
|
|
||||||
|
AudioMemory(6);
|
||||||
|
|
||||||
|
Serial.println("setup done");
|
||||||
|
|
||||||
|
if(!tonesweep1.play(t_ampx,t_lox,t_hix,t_timex)) {
|
||||||
|
Serial.println("AudioSynthToneSweep - begin failed");
|
||||||
|
while(1);
|
||||||
|
}
|
||||||
|
// wait for the sweep to end
|
||||||
|
while(tonesweep1.isPlaying());
|
||||||
|
|
||||||
|
// and now reverse the sweep
|
||||||
|
if(!tonesweep1.play(t_ampx,t_hix,t_lox,t_timex)) {
|
||||||
|
Serial.println("AudioSynthToneSweep - begin failed");
|
||||||
|
while(1);
|
||||||
|
}
|
||||||
|
// wait for the sweep to end
|
||||||
|
while(tonesweep1.isPlaying());
|
||||||
|
Serial.println("Done");
|
||||||
|
}
|
||||||
|
|
||||||
|
void loop(void){
|
||||||
|
}
|
||||||
|
|
@ -0,0 +1,146 @@
|
||||||
|
// Trellis M4 Audio Workshop
|
||||||
|
// shows how to alter pitch with accelerometer
|
||||||
|
// Waveform Mod
|
||||||
|
|
||||||
|
#include <Audio.h>
|
||||||
|
#include <Adafruit_Sensor.h>
|
||||||
|
#include <Adafruit_ADXL343.h>
|
||||||
|
#include "Adafruit_NeoTrellisM4.h"
|
||||||
|
#include <elapsedMillis.h>
|
||||||
|
|
||||||
|
Adafruit_ADXL343 accel = Adafruit_ADXL343(123, &Wire1);
|
||||||
|
|
||||||
|
// The NeoTrellisM4 object is a keypad and neopixel strip subclass
|
||||||
|
// that does things like auto-update the NeoPixels and stuff!
|
||||||
|
Adafruit_NeoTrellisM4 trellis = Adafruit_NeoTrellisM4();
|
||||||
|
// Paste your Audio System Design Tool code below this line:
|
||||||
|
// GUItool: begin automatically generated code
|
||||||
|
AudioSynthWaveform waveform1; //xy=592.7221984863281,187.38888549804688
|
||||||
|
AudioOutputAnalogStereo audioOutput; //xy=777.0833129882812,189.08334350585938
|
||||||
|
AudioConnection patchCord1(waveform1, 0, audioOutput, 0);
|
||||||
|
AudioConnection patchCord2(waveform1, 0, audioOutput, 1);
|
||||||
|
// GUItool: end automatically generated code
|
||||||
|
|
||||||
|
|
||||||
|
int xbend = 64;
|
||||||
|
int ybend = 64;
|
||||||
|
int last_xbend = 64;
|
||||||
|
int last_ybend = 64;
|
||||||
|
|
||||||
|
int count=1;
|
||||||
|
|
||||||
|
void setup() {
|
||||||
|
trellis.begin();
|
||||||
|
trellis.show(); // Initialize w all pixels off
|
||||||
|
trellis.setBrightness(255);
|
||||||
|
|
||||||
|
if(!accel.begin()) {
|
||||||
|
Serial.println("No accelerometer found");
|
||||||
|
while(1);
|
||||||
|
}
|
||||||
|
AudioMemory(10);
|
||||||
|
// Initialize processor and memory measurements
|
||||||
|
AudioProcessorUsageMaxReset();
|
||||||
|
AudioMemoryUsageMaxReset();
|
||||||
|
Serial.begin(115200);
|
||||||
|
waveform1.begin(WAVEFORM_SAWTOOTH);
|
||||||
|
delay(1000);
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
void loop() {
|
||||||
|
waveform1.frequency(110 + (ybend * 2));
|
||||||
|
waveform1.amplitude(0.05);
|
||||||
|
wait(5);
|
||||||
|
}
|
||||||
|
|
||||||
|
void wait(unsigned int milliseconds){
|
||||||
|
elapsedMillis msec=0;
|
||||||
|
while (msec <= milliseconds){
|
||||||
|
trellis.tick();
|
||||||
|
while(trellis.available()) {
|
||||||
|
keypadEvent e = trellis.read();
|
||||||
|
Serial.print((int)e.bit.KEY);
|
||||||
|
int keyindex = e.bit.KEY;
|
||||||
|
if(e.bit.EVENT == KEY_JUST_PRESSED){
|
||||||
|
Serial.println(" pressed");
|
||||||
|
trellis.setPixelColor(keyindex, Wheel(keyindex * 255 / 32)); // rainbow!
|
||||||
|
}
|
||||||
|
else if(e.bit.EVENT == KEY_JUST_RELEASED){
|
||||||
|
Serial.println(" released");
|
||||||
|
trellis.setPixelColor(keyindex, 0);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
// Check for accelerometer
|
||||||
|
sensors_event_t event;
|
||||||
|
accel.getEvent(&event);
|
||||||
|
|
||||||
|
//check if it's been moved a decent amount
|
||||||
|
if (abs(event.acceleration.x) < 2.0) { // 2.0 m/s^2
|
||||||
|
// don't make any bend unless they've really started moving it
|
||||||
|
xbend = 64;
|
||||||
|
}
|
||||||
|
else {
|
||||||
|
if (event.acceleration.x > 0) {
|
||||||
|
xbend = ofMap(event.acceleration.x, 2.0, 10.0, 63, 0, true); // 2 ~ 10 m/s^2 is upward bend
|
||||||
|
}
|
||||||
|
else {
|
||||||
|
xbend = ofMap(event.acceleration.x, -2.0, -10.0, 64, 127, true); // -2 ~ -10 m/s^2 is downward bend
|
||||||
|
}
|
||||||
|
}
|
||||||
|
if (xbend != last_xbend) {
|
||||||
|
Serial.print("X mod: "); Serial.println(xbend);
|
||||||
|
last_xbend = xbend;
|
||||||
|
}
|
||||||
|
|
||||||
|
if (abs(event.acceleration.y) < 2.0) { // 2.0 m/s^2
|
||||||
|
ybend = 64;
|
||||||
|
}
|
||||||
|
else {
|
||||||
|
if (event.acceleration.y > 0) {
|
||||||
|
ybend = ofMap(event.acceleration.y, 2.0, 10.0, 63, 0, true); // 2 ~ 10 m/s^2 is upward bend
|
||||||
|
}
|
||||||
|
else {
|
||||||
|
ybend = ofMap(event.acceleration.y, -2.0, -10.0, 64, 127, true); // -2 ~ -10 m/s^2 is downward bend
|
||||||
|
}
|
||||||
|
}
|
||||||
|
if (ybend != last_ybend) {
|
||||||
|
Serial.print("Y mod: "); Serial.println(ybend);
|
||||||
|
last_ybend = ybend;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
// Input a value 0 to 255 to get a color value.
|
||||||
|
// The colours are a transition r - g - b - back to r.
|
||||||
|
uint32_t Wheel(byte WheelPos) {
|
||||||
|
WheelPos = 255 - WheelPos;
|
||||||
|
if(WheelPos < 85) {
|
||||||
|
return Adafruit_NeoPixel::Color(255 - WheelPos * 3, 0, WheelPos * 3);
|
||||||
|
}
|
||||||
|
if(WheelPos < 170) {
|
||||||
|
WheelPos -= 85;
|
||||||
|
return Adafruit_NeoPixel::Color(0, WheelPos * 3, 255 - WheelPos * 3);
|
||||||
|
}
|
||||||
|
WheelPos -= 170;
|
||||||
|
return Adafruit_NeoPixel::Color(WheelPos * 3, 255 - WheelPos * 3, 0);
|
||||||
|
}
|
||||||
|
|
||||||
|
// floating point map
|
||||||
|
float ofMap(float value, float inputMin, float inputMax, float outputMin, float outputMax, bool clamp) {
|
||||||
|
float outVal = ((value - inputMin) / (inputMax - inputMin) * (outputMax - outputMin) + outputMin);
|
||||||
|
|
||||||
|
if (clamp) {
|
||||||
|
if (outputMax < outputMin) {
|
||||||
|
if (outVal < outputMax) outVal = outputMax;
|
||||||
|
else if (outVal > outputMin) outVal = outputMin;
|
||||||
|
} else {
|
||||||
|
if (outVal > outputMax) outVal = outputMax;
|
||||||
|
else if (outVal < outputMin) outVal = outputMin;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
return outVal;
|
||||||
|
|
||||||
|
}
|
||||||
Loading…
Reference in a new issue