科学の箱

科学・IT・登山の話題

バイオリン

midiシーケンサで調べたことをまとめる

投稿日:

シーケンサと対比するのはレシーバである。レシーバではリアルタイムに指定したノートを送信できる。例えばユーザーの入力に合わせて音を鳴らしたいときにはレシーバを使う。

それに対してシーケンサはあらかじめ作成したノートの集合、つまり曲が記録されている。シーケンサではスタートするだけですべてのノートが再生される。レシーバと違いコードの中で再生のタイミングを図ったり、繰り返し同じノートの動作を命令する必要がない。

javax.sound APIではmidiシーケンサはMidiSystem.getSequencer()で取得できる。

シーケンサにおける時間単位はチックまたはマイクロ秒単位になる。

シーケンサにはノートのon/offを記録する。このときティック単位で時間を表す。例えば時間0でonにするならば、ティック=0でonとする。時間480でoffにするのならばティック=480でoffにする。ティックはシーケンサにおける時間単位になるが実際の絶対時間を示しているわけではない。

シーケンサにはPPQ: pulse per quater note, 1ティックが四分音符に対応するティック数を指定する。ティックが大きくなればテンポが遅くなるし、小さくなればテンポが速くなる。ただしシーケンサの中で1つのPPQしか取れない。

ティックに対する時間はマイクロ秒で指定することができる。四分音符 -> ティック数 -> 秒数という関係になる。四分音符自体には秒数が関連付けられていない。これによりマイクロ秒/ティックを変更するだけでテンポを操作できる。この単位はトラック単位で指定できる。

ノートを記録するのはトラックと呼ばれる。トラックは複数シーケンサに記録できるのでシーケンサでトラックを選ぶことで異なった曲を選択できる。

midiシーケンサを使って連続的に音を出してみた。


package midi06;

import javax.sound.midi.*;

import java.util.*;

public class midi06main {
    public static void main(String[] args) throws Exception {
    	/* 69, 74, 76, 79 */
    	int[] notenums = { 69, 74, 76, 79 };
    	
        Sequencer sequencer = null;
        try {
            sequencer = MidiSystem.getSequencer();
            sequencer.open();

            Sequence seq = new Sequence(Sequence.PPQ, 240);
            Track track = seq.createTrack();

            MetaMessage tempo = new MetaMessage();
            tempo.setMessage(0x51, new byte[] {0x07, (byte)0xa1, 0x20}, 3);
            track.add(new MidiEvent(tempo, 0));
/* for loopにする前のコード
            int duration = 0;
            int buffer = 120;
            ShortMessage note69on = new ShortMessage();
            note69on.setMessage(ShortMessage.NOTE_ON, 69, 127);
            track.add(new MidiEvent(note69on, 0));
            ShortMessage note69off = new ShortMessage();
            note69off.setMessage(ShortMessage.NOTE_OFF, 69, 0);
            track.add(new MidiEvent(note69off, duration += buffer));

            ShortMessage note74on = new ShortMessage();
            note74on.setMessage(ShortMessage.NOTE_ON, 74, 127);
            track.add(new MidiEvent(note74on, duration += buffer));
            ShortMessage note74off = new ShortMessage();
            note74off.setMessage(ShortMessage.NOTE_OFF, 74, 0);
            track.add(new MidiEvent(note74off, duration += buffer));

            ShortMessage note76on = new ShortMessage();
            note76on.setMessage(ShortMessage.NOTE_ON, 76, 127);
            track.add(new MidiEvent(note76on, duration += buffer));
            ShortMessage note76off = new ShortMessage();
            note76off.setMessage(ShortMessage.NOTE_OFF, 76, 0);
            track.add(new MidiEvent(note76off, duration += buffer));

            ShortMessage note79on = new ShortMessage();
            note79on.setMessage(ShortMessage.NOTE_ON, 79, 127);
            track.add(new MidiEvent(note79on, duration += buffer));
            ShortMessage note79off = new ShortMessage();
            note79off.setMessage(ShortMessage.NOTE_OFF, 79, 0);
            track.add(new MidiEvent(note79off, duration += buffer));
*/
            int duration = 0;
            int buffer = 480;
            int index = 0;
            ShortMessage[] notes = new ShortMessage[notenums.length * 2];
            for(int num : notenums) {
            	
            	notes[index] = new ShortMessage();
	            notes[index].setMessage(ShortMessage.NOTE_ON, num, 127);
	            track.add(new MidiEvent(notes[index], duration));
	            duration += buffer;
	            index++;
	            
	            notes[index] = new ShortMessage();
	            notes[index].setMessage(ShortMessage.NOTE_OFF, num, 0);
	            track.add(new MidiEvent(notes[index], duration));
	            duration += buffer;
	            index++;
	        }
            sequencer.setSequence(seq);
            sequencer.start();
            while (sequencer.isRunning()) Thread.sleep(10000);
        }
        finally {
            if (sequencer != null && sequencer.isOpen()) sequencer.close();
        }
    }
}


メタ情報

inarticle



メタ情報

inarticle



-バイオリン
-, ,

執筆者:


comment

メールアドレスが公開されることはありません。 * が付いている欄は必須項目です

関連記事

no image

バイオリンのチューナーを作る – midiについて調べた

バイオリンのチューナーアプリを作ろうと思い立ち調査を開始。 PC上で音楽関連の操作をするにはmidiを利用する。javaではすでにjavax.soud.midiパッケージが提供されている。 midiで …

no image

midiで入力デバイスの一覧を取得する

マイクロフォンを使いmidiで録音をしてみる。下記のページからmidiデバイスの一覧を取得したが、肝心のマイクロフォンが含まれていない。 バイオリンのチューナーを作る – midiをさらに …

no image

バイオリンのチューナーを作る – midiをさらに掘り下げた

midiについてさらに掘り下げてみた。 連続したノートの演奏 まず前日のソースコードから連続で違うノートを演奏してみた。連続で音を演奏するためには前の音を消す必要がある。消さないと同時に音が鳴り響くた …

2013年11月
« 10月   12月 »
 123
45678910
11121314151617
18192021222324
252627282930  

side bar top



アーカイブ

カテゴリー