SSブログ

Digisparkで複数のタクトスイッチを扱う [Arduino]

Digisparkは使用できるピンが少ないので工夫が必要。
analogRead()で複数のタクトスイッチを扱う方法が、以下のページです。

I/Oピン一つで読めるキーパッドの設計サービス
https://synapse.kyoto/tool/ResDiv/page001.html

抵抗分圧により複数のボタンの識別をしています。
ライブラリもあるようですが、ブラックボックス化したくないので自作します。
抵抗値の計算もできますが、大まかな値を確認し、自分が持っている抵抗(E6系列中心でまちまち)でもできるよう、エクセルで分圧の計算もしました。

 Vout= Vcc × (R2+R3+…+Rn) / (R1+R2+…+Rn)

閾値は、それぞれの分圧の中間値として、それを10ビット(0~1023)の値に換算しました。
resvoldiv.png
あと、analogRead()は遅いらしいので、すべてのボタンは押されたときの電圧がdigitalRead()のLow判定電圧未満としておき、digitalRead()でLowになったら、あらためてanalogRead()で値を読むということにしました。

digitalRead()のLow判定電圧ですが、

Arduino Unoの入力スレッショルド電圧を測ってみる(閾値電圧) | のぶらぼ
https://nobulabo.com/arduino-uno-threshold-level/

「HIGH⇒LOW(VIL)は2.2V、LOW⇒HIGH(VIH)は2.6V、その差であるヒステリシス電圧は0.4Vであることがわかりました。」
とありました。

ATtiny25/V / 45/V / 85/V のデータシート
https://ww1.microchip.com/downloads/en/DeviceDoc/Atmel-2586-AVR-8-bit-Microcontroller-ATtiny25-ATtiny45-ATtiny85_Datasheet.pdf

186, 187ページの「22.7 Pin Threshold and Hysteresis」の項目をみるとVcc 5Vのとき
HIGH⇒LOW(VIL)は2.25V、LOW⇒HIGH(VIH)は2.5V あたりです。

タクトスイッチが押されたとき(HIGH⇒LOW)を確認したいので、分圧電圧を2.25V未満に抑えることにしました。



押されたボタン(SW1~SW4)の番号の回数分 LEDを点滅させるスケッチです。
// Check multiple buttons with one pin for digispark
//
//   Vcc--R1--+----+-R2-+-R3-+-R4-+      (R1:4.7k, R2:680, R3,R4:1k)
//            |   sw1  sw2  sw3  sw4
//            P2   +----+----+----+----GND
//
const uint16_t Vth[] = {0,  64, 199, 320};  // threshold (intermediate value between voltages -> 10bit)

void setup() {
  pinMode(2, INPUT);                        // P2:Buttons (D2/A1)
  pinMode(1, OUTPUT);                       // P1:Built-in LED (D1)
}

void loop() {
  uint8_t  btn=0;                           // pressed button number (0 if none are pressed)
  uint16_t val;                             // variable to store the value read
  if( !digitalRead(2) ) {                   // Read Button number
    delay(10);                                              // chattering control
    val = analogRead(1);                                    // read the input pin
    for(btn=1; btn<sizeof(Vth)>>1 && val>Vth[btn]; btn++);  // Advance the btn until the Vth is exceeded
    while( !digitalRead(2) );                               // Wait until the button is released 
  }
  for(; btn; btn--) {                       // Blinks the LED for the number of button numbers
    digitalWrite(1, HIGH);
    delay(100);
    digitalWrite(1, LOW);
    delay(200);
  }
}

タグ:Digispark
nice!(0)  コメント(0) 

nice! 0

コメント 0

コメントを書く

お名前:
URL:
コメント:
画像認証:
下の画像に表示されている文字を入力してください。