Arduino 16步音序器 - 音符不同步

时间:2017-03-06 10:06:25

标签: arduino midi

我使用以下代码为我的arduino mega发送midi时钟到我的鼓机&合成器。 当我还尝试在' beat'上发送midi音符时出现问题。 只有第一个音符完全同步,其余音符不同步,您可以听到它。 代码中是否有任何明显的缺陷?

// METRONOME
#include <MIDI.h>

#define LED1PIN 13
#define LED4PIN 7
#define SWITCHAPIN 5
#define SWITCHBPIN 2
MIDI_CREATE_INSTANCE(HardwareSerial, Serial1, MIDI);

void setup() {
  pinMode(LED1PIN, OUTPUT);
  pinMode(LED4PIN, OUTPUT);

  pinMode(SWITCHAPIN, INPUT);
  pinMode(SWITCHBPIN, INPUT);

  digitalWrite(SWITCHAPIN, HIGH);
  digitalWrite(SWITCHBPIN, HIGH);

  MIDI.begin(MIDI_CHANNEL_OMNI);
  Serial.begin(9600);
  Serial.println("Setting up");
}

unsigned long nextClockTime = 0;
int clockDelay = 20;
int tickCount = 0;
byte running = 0;
int pula = 0;
int currentStep = 1;
int lastPulse = 0;
int currPulse = 0;
int nextTickCount = 0;

typedef struct {
  int noteNumber;
  int velocity;
  int noteLength;
  bool enabled;
}
Step;

Step stepData[100];

void loop() {

  stepData[0].enabled = true;
  stepData[0].velocity = 127;
  stepData[0].noteNumber = 40;
  stepData[23].enabled = true;
  stepData[23].velocity = 127;
  stepData[23].noteNumber = 40;
  stepData[47].enabled = true;
  stepData[47].velocity = 127;
  stepData[47].noteNumber = 40;
  stepData[71].enabled = true;
  stepData[71].velocity = 127;
  stepData[71].noteNumber = 40;
  stepData[95].enabled = true;
  stepData[95].velocity = 127;
  stepData[95].noteNumber = 40;

  MIDI.read();
  unsigned long milliseconds = millis();
  if (milliseconds > nextClockTime) {
    if (running)
      MIDI.sendRealTime(MIDI_NAMESPACE::Clock);

    nextClockTime = milliseconds + clockDelay;
    nextTickCount = tickCount + 1;
    if (tickCount == 0) {
      if (stepData[tickCount].enabled) {
        MIDI.sendNoteOn(stepData[tickCount].noteNumber, stepData[tickCount].velocity, 1);
        Serial.print("STEP ENABLED: ");
        Serial.println(tickCount);
      }
    }
    if (tickCount == 23) {
      if (stepData[tickCount].enabled) {
        MIDI.sendNoteOn(stepData[tickCount].noteNumber, stepData[tickCount].velocity, 1);
        Serial.print("STEP ENABLED: ");
        Serial.println(tickCount);
        currPulse = millis(); //1500
        Serial.println(currPulse - lastPulse); //1500-500
        lastPulse = currPulse;
      }
    }
    if (tickCount == 47) {
      if (stepData[tickCount].enabled) {
        MIDI.sendNoteOn(stepData[tickCount].noteNumber, stepData[tickCount].velocity, 1);
        Serial.print("STEP ENABLED: ");
        Serial.println(tickCount);
        currPulse = millis();
        Serial.println(currPulse - lastPulse);
        lastPulse = currPulse;
      }
    }
    if (tickCount == 71) {
      if (stepData[tickCount].enabled) {
        MIDI.sendNoteOn(stepData[tickCount].noteNumber, stepData[tickCount].velocity, 1);
        Serial.print("STEP ENABLED: ");
        Serial.println(tickCount);
        currPulse = millis();
        Serial.println(currPulse - lastPulse);
        lastPulse = currPulse;
      }
    }
    if (tickCount == 95) {
      if (stepData[tickCount].enabled) {
        //MIDI.sendNoteOn(stepData[tickCount].noteNumber, stepData[tickCount].velocity, 1);
        Serial.print("STEP ENABLED: ");
        Serial.println(tickCount);
        currPulse = millis();
        Serial.println(currPulse - lastPulse);
        lastPulse = currPulse;
      }
      nextTickCount = 0;
    }
    tickCount = nextTickCount;
  } else if (digitalRead(SWITCHBPIN) == LOW) {
    if (running) {
      MIDI.sendRealTime(MIDI_NAMESPACE::Stop);
      running = 0;
      digitalWrite(LED4PIN, LOW);
    }
  } else {
    clockDelay = analogRead(A0) / 10;
  }
  if (pula == 0) {
    if (!running) {
      MIDI.sendRealTime(MIDI_NAMESPACE::Start);
      tickCount = 0;
      running = 1;
      digitalWrite(LED4PIN, HIGH);
      pula = 1;
    }
  }
}

1 个答案:

答案 0 :(得分:1)

节拍间距不均匀。 24 - 1是23,48 - 24是24等。

一个简单的解决方法是将你的第一个节拍设置为0而不是1.而不是递增tickCount,将变量nextTickCount设置为tickCount +1,并将其分配给if (milliseconds > nextClockTime) {条件括号末尾的tickCount。

另外,当tickCount达到95时,将nextTickCount设置为0,但不播放任何音符(它将在0拍上播放)