Arduino+YMZ294を光センサ経由で操作

だいぶ前に買ったまま放置していたCdS(光センサ)の存在を思い出したので、PSGの回路で使ってみました。

1000個もいらん(汗
秋月電子では40円からあります。

5Vから10kΩ抵抗経由でGNDに落とす途中にアナログ入力の0番につなぎます。
CdS
こんな感じ。

スケッチはこちら。

#include <YMZ294.h>

// Output Pins
const byte WRCS_PIN = 8;
const byte A0_PIN = 9;
const byte RESET_PIN = 10;

YMZ294 ymz(WRCS_PIN, A0_PIN, RESET_PIN);

void setup() {
  DDRD = 0b11111111;
  pinMode(WRCS_PIN, OUTPUT);
  pinMode(A0_PIN, OUTPUT);
  pinMode(RESET_PIN, OUTPUT);
  
  ymz.Reset();
  ymz.SetMixer(0b111, 0b100);
  ymz.SetVolume(CH_A, 0b00001111);
  ymz.SetFreqBit(CH_A, 0);
  ymz.SetVolume(CH_B, 0b00001111);
  ymz.SetFreqBit(CH_B, 0);
}

word value;
void loop() {
  value = 1024 - analogRead(0);
  
  ymz.SetFreqBit(CH_A, value);
  ymz.SetFreqBit(CH_B, value);

  delay(10);
}


analogRead()で取ってきた値を音程として与えてます。
そのままYMZ294に食わせてもいいんですが、その場合、明るい方が低い音で暗い方が高い音になるので、逆のほうが面白そうだってことで1024 – analogRead(0)にしてます。
delay()は10ミリ秒。てきとーです。
ちなみに動画で使ってるのは自転車用のライト。一段階暗くした状態(17秒くらい)の音が、ファミコン版火の鳥で我王が死んだ時の音に似てる気がする。

もう一個。こちらは前回のリズムマシン風ノイズを操作してます。

回路は矩形波の方と同じ。
スケッチも前回とそう変わってないんですが、一応。

#include <YMZ294.h>

// Output Pins
const byte WRCS_PIN = 8;
const byte A0_PIN = 9;
const byte RESET_PIN = 10;

YMZ294 ymz(WRCS_PIN, A0_PIN, RESET_PIN);

void setup() {
  DDRD = 0b11111111;
  pinMode(WRCS_PIN, OUTPUT);
  pinMode(A0_PIN, OUTPUT);
  pinMode(RESET_PIN, OUTPUT);
  
  ymz.Reset();
  ymz.SetMixer(0b111, 0b000);
  ymz.SetVolume(CH_A, 0b00001111);
  ymz.SetFreqBit(CH_A, 0);
  ymz.SetVolume(CH_B, 0b00001111);
  ymz.SetFreqBit(CH_B, 0);
  ymz.SetVolume(CH_C, 0b00001111);
  ymz.SetFreqBit(CH_C, 0);
}

byte beats[6][2] = {
  {0b00100, 8},
  {0b00001, 12},
  {0b00010, 8},
  {0b01000, 64},
  {0b00010, 8},
  {0b00010, 16},
};
 
void loop() {
  static word noteGate = 192;
  static unsigned long lastMSec = 0;
  static byte state = 0;
  static byte step = 0;

  unsigned long diffMSec = millis() - lastMSec;

  noteGate = 256 - (analogRead(0) >> 2);
  
  switch (state){
    case 0: // Note Off to On
      ymz.SetNoiseFreqBit(beats[step][0]);
      TurnNoise(true);
      state = 1;
      break;
    case 1: // Step Time Over
      if (diffMSec > beats[step][1]){
        TurnNoise(false);
        state = 2;
      }
      break;
    case 2: // Gate Time Over (Note Off)
      if (diffMSec > noteGate){
        state = 0; // Initialize
        lastMSec = millis();
        if (++step >= (sizeof(beats) / 2))
          step = 0;
      }
      break;
  }
}

void TurnNoise(bool isNoise){
  if (isNoise)
    ymz.SetMixer(0b000, 0b000);
  else
    ymz.SetMixer(0b111, 0b000);
}


こちらは周波数として与えてもあんまりおもしろくないので、半固定抵抗の時と同様、テンポを変えるのにCdSを使ってます。
明るい→テンポ早め、暗い→テンポ遅めにするために、noteGate = 256 – (analogRead(0) >> 2)としてます。

さて、こいつを応用すれば、なんかもっとおもしろい事ができそうな気がするんですが、ちょっとまだ思いつかないのでとりあえずここまで。また明日にでも考えます。

コメントを残す