シーケンサについて、初歩的な説明のメモ。

音楽機材におけるシーケンサを作るのって凄い難しそうなイメージがあります。
かくいう自分もそうだったし、必須となる機能がないとどうやって作るの?というのが当然のように疑問として浮かんできます。
最初Kiokuさん宅で自作シーケンサのプログラム(デモで走らせる音楽のエディタ)見せてもらったけど、よくわからんかったのを覚えてます。
今考えると「こうやってたんだろーなー」ってあたりが付きますが。

ですが、勘所を抑えるとそれほど難しくないので、まずはシーケンサの機能と実装についてメモっておこうかと。

あとは自分が設計に困ったときに見返せるような文章にしておくのが良さそうだなあと考えまとめておくものです。

シーケンサとは一体何か

一言でいうと、「スケジュールを立てた順番で音を再生する装置・ソフトウェア」というものになります。
シーケンス、つまり「自動制御であらかじめ定められた動作の順序」を再生するためのシステム及びソフトウェアになります。

音楽だけではなく、作業用機器に対してもシーケンスという言葉が使われるみたいですね。

シーケンサの内部処理

自分が知ってる範囲で汎用化して処理を落とし込んでみます。

  • 毎秒もしくは延々と処理するループ処理の中で、ループ間の時間を計測する
  • 計測した時間をトータルに加算し、前の発音と次の発音との時間間隔を超えた場合、次の発音処理を起動する
  • 以降、1~2番目の処理を再生時延々と繰り返す

言ってしまうとこんだけです。

例えばこれが正確な時間を取れればイベントハンドリングみたいな形でも問題ないのですが、
結局のところ秒数をどこでカウントするかと言うと別にタイマ割り込みみたいな関数で秒数を計算して
時間検出するという形になるかと思いますし、それだったら見える範囲で処理書いてしまったほうが早いです。

あと上記の方法だと、「時間を正確に取ることができません」。
内部構造として「しきい値を超えたら処理する」形のため、ピッタリの時間で処理は不可能ということです。

ただ、ピッタリじゃないと言ってもミリ秒単位(場合によってはナノ秒単位)なので、
それほど違和感は出ないかと思います。

結局の所、トータル秒数が合ってれば演奏に問題がないよ、という形になりますし、
オフラインバウンスで演奏させるなら、別の方法で正確に演奏できます。

実装の一例

  • タイマ割り込みで秒数をカウント、規程秒数を超えたら次の譜面に移行
  • 基本のループ関数にて秒数をカウント、規程秒数を超えたら次の譜面に移行
  • コールバック関数にて再生予定のバッファ数から想定秒数をカウント、規程秒数を超えたら次の譜面に移行

どれも大きく違う設計にはなりませんね。

1番目は組み込み機器とかで実装するのが一番確実ですし、
2番目はコマンドラインみたいなアプリケーションやArduinoみたいなプラットフォームでも有効です。
3番目は主にWindowsみたいなイベントドリブンの環境用の実装になりますが、
カウントする秒数をどこから算出するかという問題しかないので、WAVを作成するためのバッファがあれば
サンプリングレートから秒数を算出することが可能です。

実際、自作キーボードである「umbra」シリーズのシーケンサは上記の方法で実装してます。
(ATmega上のタイマ割り込みで計算してみましたが、1ループで大量に処理しなければ問題がでない模様)