📋 คัดลอกโค้ด
#include <math.h>
// ================= MUX =================
#define S0 20
#define S1 19
#define S2 18
#define S3 17
#define SIG 16
// ================= AUDIO =================
#define AUDIO_PIN 21
#define SAMPLE_RATE 22050
// ================= LED & CONTROLS =================
#define LED_PIN 22
#define RIFF_BUTTON 8
#define VOICES 4
// NOTE TABLE (Frequencies for C, C#, D, etc.)
float noteTable[12] = {
261.63, 277.18, 293.66, 311.13, 329.63, 349.23,
369.99, 392.00, 415.30, 440.00, 466.16, 523.25
};
int keyMap[12] = {1, 3, 6, 0, 11, 8, 9, 7, 5, 4, 2, 0};
// VARIABLES
float phase[VOICES], subPhase[VOICES], freq[VOICES], env[VOICES];
bool voiceActive[VOICES];
float cutoff = 1200, lpState = 0;
int octave = 0;
float distortionAmount = 0;
bool distortionUp = true, distortionFadeOn = false;
unsigned long lastDistUpdate = 0;
#define DIST_FADE_INTERVAL 20
#define DIST_STEP 0.05
bool drumOn = false;
unsigned long lastStep = 0;
int stepMs = 500;
float kickEnv = 0, kickPhase = 0;
float riffNotes[] = {329.63, 329.63, 392.00, 329.63, 293.66, 261.63, 246.94, 220.00};
int riffLength = 8, riffStep = 0;
bool riffPlaying = false;
unsigned long riffTimer = 0;
int riffNoteDuration = 450;
unsigned long lastAudio = 0, lastScan = 0;
float ledLevel = 0;
void selectMux(uint8_t ch) {
digitalWrite(S0, (ch & 1) ? HIGH : LOW);
digitalWrite(S1, (ch & 2) ? HIGH : LOW);
digitalWrite(S2, (ch & 4) ? HIGH : LOW);
digitalWrite(S3, (ch & 8) ? HIGH : LOW);
delayMicroseconds(5);
}
bool readButton(uint8_t ch) {
selectMux(ch);
return digitalRead(SIG) == LOW;
}
void handleDistortionFade() {
if(!distortionFadeOn) return;
unsigned long now = millis();
if(now - lastDistUpdate < DIST_FADE_INTERVAL) return;
lastDistUpdate = now;
if(distortionUp) {
distortionAmount += DIST_STEP;
if(distortionAmount >= 1) { distortionAmount = 1; distortionUp = false; }
} else {
distortionAmount -= DIST_STEP;
if(distortionAmount <= 0) { distortionAmount = 0; distortionUp = true; }
}
}
void setup() {
pinMode(S0, OUTPUT); pinMode(S1, OUTPUT); pinMode(S2, OUTPUT); pinMode(S3, OUTPUT);
pinMode(SIG, INPUT_PULLUP);
pinMode(AUDIO_PIN, OUTPUT); pinMode(LED_PIN, OUTPUT);
pinMode(RIFF_BUTTON, INPUT_PULLUP);
analogWriteResolution(10);
analogWriteFreq(62500);
for(int i=0; i 3000) {
lastScan = now;
bool pressed[12];
for(int i=0; i<12; i++) pressed[i] = readButton(i);
int v = 0;
for(int i=0; i<12; i++) {
if(pressed[i] && v < VOICES) {
freq[v] = noteTable[keyMap[i]] * pow(2, octave);
voiceActive[v] = true;
v++;
}
}
for(int i=v; i