Arduinoを USB/HIDデバイス(仮想キーボード)として活用する(第四回) 「radiko(ラジコ)を Arduino から操作する」


本記事について

 Arduinoを USB/HIDデバイスとして活用する第四回です。第三回はここ。前回の予告から方針を変えました(^_^;)。今回は仮想キーボードの実用例として、 radiko(ラジコ)の ON/OFFとチャンネル切り替えを紹介します。

第四回)「radiko(ラジコ)を Arduino から操作する」

 Arduinoの USB/HID を使って文字列を出力することで、 radiko をON/OFFしたり、チャンネル切り替えをおこないます。操作は Arduinoに設置したSW二つを使って行います。USB/HIDからブラウザーへの上り通信だけで実現しています。下り通信はありません。

機能概要

PCのブラウザーにUSB/HID出力することによってradikoを聴くことができます。SW操作で決められた文字列を出力することで radikoを操作することができます。
・Setup処理
 ・周辺デバイスを初期化する
 ・所定時間後待って、Loop処理に移行
・Loop処理
 ・定時間隔毎、処理を繰り返し実施
 ・SW1の押下で 指定されたチャンネルのURLをUSB/HID出力し、radikoをONにする。radikoがONの時はOFFにする。
 ・SW2の押下で、次回のチャンネルを1つ進める。

準備するもの

 PC (Windows10) ブラウザーは、Microsoft Edge,Chrome
 Adafruit Trinket M0
 開発環境は Windows版の Arduino IDE v1.8.9

全体の仕組み

PCはネットに接続できること。Adafruit Trinket M0にはSWが二つありLCDが接続されている。LCDはなくても動くが内部状態がわかりにくい場合がある。

ハード構成

Adafruit Trinket M0 周りのハード構成を示す。

ソフトウエア

apl_usbhid_TrinketM0_04Wondows.ino
/*
 *公開第四回)radiko操作 2020/06/19
 */
// WindowsPC
#define USBHOST_WINPC
//環境に合わせて内容を確認または修正すること ーーここから -----------------------------
//LCD I2Cアドレスの設定
#define LCDDEVADDR 0x3e
//②ハード設定
#define LED_PIN 13
#define SW_PIN  1
#define SW2_PIN  3
//環境に合わせて内容を確認または修正すること ーーここまで -----------------------------

#if defined USBHOST_WINPC
String g_url_string = "http'//radiko.jp/#!/live/";
#elif defined USBHOST_MAC
String g_url_string = "radiko.jp/#!/live/";
#else
/設定不備はコンパイルエラーにする
#endif
#define WCS_DELAY_T1 150 //T1 ブラウザー応答時間150
#define WCS_DELAY_GAMEN 3000  //URLたたいてから画面が表示されるまで待つ
#define WCS_SWWAIT_MAXCOUNT 30  //sw押下待ちのリトライ回数上限 30秒
#include <Wire.h>
#include <ZeroTimer.h>
#include "lib_keyboard.h"
#include "LCDManager.h"

int16_t g_pass;  //HID出力したら後の待ち時間を制御する
boolean g_I2CNormal;
boolean g_LED;
boolean g_radio_on;
volatile int g_i; //timerカウント
LCDManager myLCD;
//チャンネル定義は中部地方の例。必要にあわせて変更してください。
int g_channel; //最大3
char g_annai[3][9] = {"c1:CBC  " , "c2:TOKAI" , "c3:NHK1 "};
char g_radiko_url[3][11] = {"CBC       " , "TOKAIRADIO" , "JOCK      "};
//
//
//
void setup(){
  char w_buf[9];
  g_pass = 1;
  g_i = 0;
  g_LED = false;
  g_radio_on = false;
  g_channel = 0;
  pinMode(LED_PIN,OUTPUT);
  pinMode(SW_PIN, INPUT_PULLUP);
  pinMode(SW2_PIN, INPUT_PULLUP);

  Wire.begin();
  delay(100); //I2Cデバイスの初期化待ち
  //
  if (myLCD.begin(LCDDEVADDR) == false) g_I2CNormal = false;
  else g_I2CNormal = true;
  //
  strcpy(w_buf, " )pushSW");
#if defined USBHOST_WINPC
  sub_kbd_begin(1);  //Windows用に初期化
  w_buf[0] = 'W';
#elif defined USBHOST_MAC
  sub_kbd_begin(2);  //Mac用に初期化
  w_buf[0] = 'M';
#endif
  //
  sub_fw_Blink(LED_PIN, 3, 50); //動き始めたことを知らせる
  delay(100); //HIDデバイスの初期化待ち
  if (g_I2CNormal) myLCD.printStrC1(w_buf);
  if (g_I2CNormal) myLCD.printStrC0(g_annai[g_channel]);
  //
  sub_fw_timerset();  //タイマー起動
}

環境に合わせて、以下の内容を確認または修正してください
//①LCD I2Cアドレスの設定
//#define LCDDEVADDR 0x3e
②ハード設定が間違いないか確認
 LED_PIN 13
 SW_PIN 1
 SW2_PIN 3

loop処理
//
//main loop
//
void loop(){
  // 20x1=20msec毎に処理を行う
  if (sub_fw_event(1)) sub_proc();
}
//
//USB/HID処理
//
void sub_proc() {
  int j;

  //待ち時間がゼロになるまで何もしない。
  if (g_pass-- >= 0 ) return;

  if (sub_fw_SWcheck(0, SW_PIN) == 2) {
    if (g_radio_on) {
      //Enterを出して止める
      sub_apl_key2();
      if (g_I2CNormal) myLCD.printStrC1("Chan.OFF");
    } else {
      //URL+Tabx3を出す。画面が表示されるまで待つのもこの関数内
      if (g_I2CNormal) myLCD.printStrC1("URL out ");
      sub_initurl();
      sub_apl_key();
      if (g_I2CNormal) myLCD.printStrC1("Chan.ON ");
    }
    g_radio_on = !g_radio_on;
  } else if (sub_fw_SWcheck(1, SW2_PIN) == 2) {
    //channel 切替
    if (g_channel>1) g_channel = 0;
    else g_channel++;

    if (g_I2CNormal) myLCD.printStrC0(g_annai[g_channel]);
  } else {
    //その他は何もしない
    ;
  }
  g_pass = 1; 
}
(以下、省略。ソースコードを参照ください)

 ソースコードは、GitHubから取り出すことができます。 Windows用とMac用にわかれています。各フォルダー内のすべてのファイルを同一フォルダに保存して、Arduino IDE でコンパイルしてください。
注意)
・LCDのI2Cアドレスが間違った場合は、LCDへの表示をバイパスします。
・ツール/ボードの設定は、 Adafruit Trinket M0 です。
・radiko のチャンネルは中部地方になっています。お住まいの地方に合わせて変更してください。
 設定値:
  char g_annai[3][9] = {"c1:CBC " , "c2:TOKAI" , "c3:NHK1 "};
  char g_radiko_url[3][11] = {"CBC " , "TOKAIRADIO" , "JOCK "};

実行

準備として、PCがネット接続されていていること。

1.PCと Adafruit Trinket M0 を USB接続する。SW押下で動き出す。

2.定時間隔で SW1/ SW2待ちを繰り返す。
2-1.SW2押下で、次のチャンネルに切り替える。チャンネル名はLCDに表示します。
2-2.SW1押下で、cmd窓を開きURL文字列を入力する。続けて、Tabで再生ボタンまで飛び、Enterで再生(ON)する。
 動作確認中、Tabの数/タイミングがずれた場合や画面表示状態によっては、思ったところで再生ボタンが押せず苦労した。公開されているWebページでは、仮想キーボードの動きは画面デザインに大きく依存してしまい、やりたいことができない可能性もありそうだ。
2-3.SW1押下で、Enterを押して停止(OFF)する。同時にブラウザーのTabを閉じる。(Chromeの場合のみ)

まとめ

仮想キーボードの実用例として、radiko(ラジコ)の ON/OFFとチャンネル切り替えが確認できた。公開されているWebベージを利用する場合は、キーボード操作と画面デザインの依存度が高く、その利用範囲には限界があると感じた。

参考

Trinket M0の開発環境については、以下を参考にしました。
 https://www.denshi.club/cookbook/arduino/trinketm0/trinket-m01arduino-ide.html
以下のライブラリが必要です。
 ・ZeroTimer.h
   https://ehbtj.com/electronics/arduino-zero-timer-interrupt-library/