質問をすることでしか得られない、回答やアドバイスがある。

15分調べてもわからないことは、質問しよう!

新規登録して質問してみよう
ただいま回答率
85.37%
Processing

Processingは、オープンソースプロジェクトによるCGのためのプログラミング言語です。Javaをベースにしており、グラフィック機能に特化しています。イメージの生成やアニメーションなど、視覚的なフィードバックを簡単に得ることが可能です。

Q&A

1回答

389閲覧

processingとMIDIの同期ができない

laclac

総合スコア0

Processing

Processingは、オープンソースプロジェクトによるCGのためのプログラミング言語です。Javaをベースにしており、グラフィック機能に特化しています。イメージの生成やアニメーションなど、視覚的なフィードバックを簡単に得ることが可能です。

0グッド

0クリップ

投稿2024/08/15 04:53

編集2024/08/16 05:57

[追記]
processing3.4.5で実行してみましたところ、添付した画像のようにvoid noteOn(int channel, int pitch, int velocity)内のプログラムが実行されました。大学側がprocessing3.4.5の使用の許可がありましたら、1の問題は解決されたことになります。私の回答に少しでも時間を使ってくださった方々に感謝申し上げます。ありがとうございました。

私は9月の中旬にある大学の発表に向けて、電子ドラムとパソコンをMIDIで接続してプログラムを作りたいと思っております。電子ドラムでたたくことをマウスのクリックにみたて、太鼓の達人のような音楽ゲームやVJを作りたいと思っております。
扱う電子ドラムはyamahaのDD75で扱うMIDIインターフェースはMIDIMATE eXです。

そのために、私はまず電子ドラムでの出力データをprocessing4で標準出力させたいと考えています。

現段階ではprocessing上でMIDIデバイスを使用するために必要なMidiBusのインストールは完了し、pocketMIDIというアプリケーションを使用して電子ドラムをたたくとPCに信号が入力されていることが確認できています。以下がその信号が出ている時の画像です。
イメージ説明

参照ページに記載されているプログラムを参考にして、標準出力をするプログラムを以下のように書きました。出力した時の画像も添付しておきます。

import themidibus.*;

MidiBus myBus; // MidiBusインスタンス
void setup() {
size(300, 300); //ウインドウのサイズ
background(0); //ウインドウ背景の色

MidiBus.list(); //MIDIデバイスのリストを表示
myBus = new MidiBus(new java.lang.Object(), 2, 5); //MIDIデバイスのinput,outputを指定
}
void draw() {
int channel = 0;
int pitch = 64;
int velocity = 127;

myBus.sendNoteOn(channel, pitch, velocity); // Send a Midi noteOn
delay(200);
myBus.sendNoteOff(channel, pitch, velocity); // Send a Midi nodeOff

int number = 0;
int value = 80;

myBus.sendControllerChange(channel, number, value); // Send a controllerChange
delay(2000);
}

void noteOn(int channel, int pitch, int velocity) {
// Receive a noteOn
println();
println("Note On:");
println("--------");
println("Channel:"+channel);
println("Pitch:"+pitch);
println("Velocity:"+velocity);
}
void noteOff(int channel, int pitch, int velocity) {
// Receive a noteOff
println();
println("Note Off:");
println("--------");
println("Channel:"+channel);
println("Pitch:"+pitch);
println("Velocity:"+velocity);
}
void controlChange(int channel, int number, int value) {
// コントロールチェンジメッセージを受信したときに呼び出される
println("Control Change Received");
println("Channel: " + channel);
println("Number: " + number);
println("Value: " + value);
イメージ説明
参照ページ:https://github.com/sparks/themidibus/blob/master/examples/Basic/Basic.pde

問題点として以下の3点があります。
1.void controllerChange(int channel, int number,int value)、void noteOn(int channel, int pitch, int velocity)、void noteOff(int channel, int pitch, int velocity)のコードが読み込まれない。エラーが出ていないが、イベント内に標準出力のコードを入力しても標準出力されない。
2.そもそも、上記の引数であるchannel,number,value,pitch,velcityが扱う電子ドラムDD75とどう関係しているのかわからない。
3.アプリケーションpocketMIDIの使用方法が不明。音の出力は分かるが、表示の意味が分からない。

そこで以下の三つについてお伺いしたいです。
1.void controllerChange(int channel, int number,int value)、void noteOn(int channel, int pitch, int velocity)、void noteOff(int channel, int pitch, int velocity)のコードが読み込まれない理由は何だと考えられますか?
(追記)
myBus = new MidiBus(new java.lang.Object(), 2, 5);の部分を
myBus = new MidiBus();
myBus.registerParent(this);
myBus.addInput(2);
myBus.addOutput(5);
に書き換える方法を試してみました。エラーメッセージは表示されませんが電子ドラムを叩いても信号を出力しません。
また、inPutの指定番号を1、outPutの指定番号を4にした場合、以下のような表示がされてしまいます。
イメージ説明
イメージ説明

2.void controllerChange(int channel, int number, int value) 、void noteOn(int channel, int pitch, int velocity)、void noteOff(int channel, int pitch, int velocity)のコードが意味する内容は何ですか?MIDIの知識不足のためchannel,number,value,pitch,velocityについてもよく分かっておりません。(追記)pitchは音の高さ、velocityは音の大きさを表すことがわかりました。

3.pocket MIDI を利用して表示された文字は何を意味しますか?上のchannel,number,valuesに対応しているのでしょうか?
(追記)pocket midiのfileからpreferenceからdetailsで詳細を表示することができました。
ですが、channelは10で出力されていることがわかりました。また一行目の三つ目の数字71番が音の強さによって変化するので、velocityに関係していると考えられます。しかし、どこがpitch,number,valuesに対応しているかどうかは分かっておりません。
以下がその表示です。
イメージ説明
お時間ある時に回答をよろしくお願いします。

補足情報
電子ドラム(DD75)の取扱説明書
https://jp.yamaha.com/files/download/other_assets/6/892376/dd75_ja_om_c0.pdf
DD75のMIDI同期リファレンス
https://jp.yamaha.com/files/download/other_assets/5/892625/dd75_ja_mr_a0_web.pdf
pocketMIDIの説明ページ
https://www.morson.jp/pocketmidi-webpage/manual/pocketmidimobile/pocketmidimobile_operation_manual_ja.html

またこの投稿は他の質問サイトに投稿をしてしまいました。
理由はマルチポストの非推奨については知らず、より多くのサイトに投稿をすることで様々な意見が得られると思ったためです。
他サイトのリンクは以下の通りです。
https://detail.chiebukuro.yahoo.co.jp/qa/question_detail/q12302479777
https://qiita.com/laclac/questions/7e773799ad5cfaed4d47
https://ja.stackoverflow.com/questions/99914/processing%e3%81%a8midi%e3%83%87%e3%83%90%e3%82%a4%e3%82%b9%e3%81%ae%e5%90%8c%e6%9c%9f%e3%81%ab%e3%81%a4%e3%81%84%e3%81%a6%e8%b3%aa%e5%95%8f%e3%81%a7%e3%81%99-%e8%a6%81%e7%b4%84%e3%81%97%e3%81%9f%e8%b3%aa%e5%95%8f%e3%81%8c%e9%95%b7%e3%81%99%e3%81%8e%e3%81%a6%e3%82%bf%e3%82%a4%e3%83%88%e3%83%ab%e3%81%ab%e6%9b%b8%e3%81%91%e3%81%aa%e3%81%8b%e3%81%a3%e3%81%9f%e3%81%ae%e3%81%a7%e6%9c%ac%e6%96%87%e3%81%ab%e8%a8%98%e8%bc%89%e3%81%97%e3%81%be%e3%81%99

気になる質問をクリップする

クリップした質問は、後からいつでもMYページで確認できます。

またクリップした質問に回答があった際、通知やメールを受け取ることができます。

バッドをするには、ログインかつ

こちらの条件を満たす必要があります。

TN8001

2024/08/15 14:50 編集

[processing - processingとMIDIデバイスの同期について質問です。(要約した質問が長すぎてタイトルに書けなかったので本文に記載します。) - スタック・オーバーフロー](https://ja.stackoverflow.com/questions/99914) [[Q&A] processingとMIDIデバイスの同期ができません - Qiita](https://qiita.com/laclac/questions/7e773799ad5cfaed4d47) > やむを得ず複数のサイトに質問を投稿された場合は、質問内容にマルチポストをする理由を書き、他のサイトの投稿へのリンクを貼ってください。 また、解決した際には必ずteratail及びすべての投稿に解決した旨と、どのように解決したかを記載してください。 [ヘルプ|他のサービスにも質問投稿をしたい(してしまった)](https://teratail.com/help#posted-otherservice)
laclac

2024/08/15 15:09

お気づきありがとうございます。迅速に投稿内容を修正し、ほかの差異との投稿へのリンクを貼ります。
guest

回答1

0

1.void controllerChange(int channel, int number,int value)、void noteOn(int channel, int pitch, int velocity)、void noteOff(int channel, int pitch, int velocity)のコードが読み込まれない理由は何だと考えられますか?

本来はnew MidiBus(thisとして、このスケッチのnoteOn等をリフレクションで取得しています。
このあたりを見てnew Object()としたのでしょうが、そうするとこのスケッチのnoteOn等は何の関連もなくなります(当然呼ばれることもありません)
NullPointerException from example - fresh windows install processing 4.3 · Issue #36 · sparks/themidibus

こうするのが分かりやすいかと思います。

Processing

1//myBus = new MidiBus(new java.lang.Object(), 2, 5); 2//myBus = new MidiBus(this, 2, 5); // これがエラーにならなければいいだけの話なんだが^^; 3myBus = new MidiBus(); 4myBus.registerParent(this); 5myBus.addInput(2); 6myBus.addOutput(5);

2.void controllerChange(int channel, int number, int value) 、void noteOn(int channel, int pitch, int velocity)、void noteOff(int channel, int pitch, int velocity)のコードが意味する内容は何ですか?MIDIの知識不足のためchannel,number,value,pitch,velocityについてもよく分かっておりません。

noteOnoteOffは(鍵盤等を)押した・離したときに呼ばれます。
チャンネル番号・ノート番号(≒音程)・ベロシティ(≒音量)が渡されます。

controllerChangeはいろいろな情報があるので説明しきれません(ggってください^^;
midi control change - Google 検索

3.pocket MIDI を利用して表示された文字は何を意味しますか?上のchannel,number,valuesに対応しているのでしょうか?

基本的にはそうです。
ただしPocket MIDIは16進表記で、Processingは10進表記になっています。
Processingでprintln("Velocity:"+hex(velocity, 2));等で16進表記にするか、
hex() / Reference / Processing.org

Pocket MIDIの設定で「Details」にチェックを入れると、10進も併記されるようです。
Pocket MIDI マニュアル for Windows/Mac


rawMidiを使うと、Pocket MIDIの出力と合わせられますね(わかりやすいとは言っていない^^;

Processing

1java.util.HexFormat hex = java.util.HexFormat.ofDelimiter(" ").withUpperCase(); 2void rawMidi(byte[] data) { 3 println(hex.formatHex(data)); 4}

HexFormat (Java SE 17 & JDK 17)


別クラスを使用する例

Processing

1import java.util.HexFormat; 2import themidibus.*; 3 4MidiBus myBus; 5HexFormat hex = HexFormat.ofDelimiter(" ").withUpperCase(); 6 7void setup() { 8 MidiBus.list(); 9 10 myBus = new MidiBus(new MidiReceiver(), 2, 5); // 別クラスのインスタンスを渡す 11} 12 13void draw() { 14} 15 16// 別クラスを用意(クラス名は任意) 17public class MidiReceiver { 18 // noteOn等が欲しい場合こちらに書く 19 20 void rawMidi(byte[] data) { 21 println(hex.formatHex(data)); 22 } 23}

アプリ動画


(追記)pocket midiのfileからpreferenceからdetailsで詳細を表示することができました。
ですが、channelは10で出力されていることがわかりました。また一行目の三つ目の数字71番が音の強さによって変化するので、velocityに関係していると考えられます。しかし、どこがpitch,number,valuesに対応しているかどうかは分かっておりません。

Port1 Ch10 NoteOn 99 28 71 [E1 ( 40), 113] Port1 Ch10 NoteOn 99 28 00 [E1 ( 40), 0]

まず「99 28 71」ここの数字は16進数です(ややこしいので以下16進数には0xを付けます)

最初の0x99は2つの意味があり、0x90番台がNoteOnです。
一の位はチャンネル番号です(0x0~0xFの16個でチャンネル1~16を表します)
0x90だったら「Ch 1 NoteOn」で、0x9Fだったら「Ch16 NoteOn」です。
0x99は「Ch10 NoteOn」ということです(ドラムパートは通常Ch10)
int channelに入ってくるのは0~15のようです。
NoteOffは本来0x80番台なのですが、NoteOnでベロシティが0の場合NoteOffのコードに来ます。

次の0x28はノート番号です(10進数で40)
E1は16進数ではなくドレミのCDEです(低いミ)
int pitchがそのままノート番号で音階になりますが、ドラムの場合は割り当てられた「なにかの音」となります。

最後0x71はベロシティです(10進数で113)
厳密には違いますが音量と思えばいいでしょう。
int velocityは0~127です。

つまり「99 28 71」が元になる生データで、それをわかりやすく表示すると「Ch10 NoteOn [E1 ( 40), 113]」になるということです。

controllerChangeint numberint valueは本当にいろいろなものがあるので、実際に操作した時の数値とマニュアルや解説ページ等を見比べて頑張って解読してください^^;
MIDI:それ何? | DTM Solutions

ゲーム?に使う範囲内なら「この数値がきたらこうする」等決め打ちでいい気がします。

投稿2024/08/15 08:51

編集2024/08/16 10:10
TN8001

総合スコア9807

バッドをするには、ログインかつ

こちらの条件を満たす必要があります。

laclac

2024/08/15 14:35

ご返答誠にありがとうございます。ご返答誠にありがとうございます。 1の回答について。 プログラムに書かれている通り、myBus = new MidiBus(this, 2, 5); ではエラーが出てしまうため、 thisの部分をnullやnew java.lang.Object()と書きました。参考にしたページは以下の通りです。 https://github.com/sparks/themidibus/blob/master/src/themidibus/MidiBus.java https://github.com/sparks/themidibus/issues/36 (エラーが出なくなる理由は分かっておりませんのでそこについてもご教授いただければ幸いです。) しかしながらプログラムを書き換えたところやはりエラーが出てしまいます。このエラーはどうすれば解消されるでしょうか。 エラーはNullPointerExceptionと表示されます。 加えて、myBus.registerParent(this); myBus.addInput(2); myBus.addOutput(5);というコードは myBus = new MidiBus(this, 2, 5); をかみ砕いて記述したものという理解でよろしいでしょうか。 2の回答について。 勉強になります。ありがとうございます。
TN8001

2024/08/15 14:44

> (エラーが出なくなる理由は分かっておりませんのでそこについてもご教授いただければ幸いです。) わたしはよくわかっていません。 これで直っているようなのですが、なぜかそのバージョンが公開されていません。 [Fix themidibus with Processing 4 by micycle1 · Pull Request #29 · sparks/themidibus](https://github.com/sparks/themidibus/pull/29) > しかしながらプログラムを書き換えたところやはりエラーが出てしまいます。このエラーはどうすれば解消されるでしょうか。 どう変えたのですか? > をかみ砕いて記述したものという理解でよろしいでしょうか。 そうです。本来1行で書けるのですが、NullPointerException回避のため分けました。 「回避のため分けた」というより、「分けたらNullPointerExceptionがでなくなった」が実際ですが^^;
laclac

2024/08/15 15:18

myBus = new MidiBus(this, 2, 5); の部分を myBus = new MidiBus(); myBus.registerParent(this); myBus.addInput(2); myBus.addOutput(5); に変えたということです
TN8001

2024/08/15 15:30

それでもエラーになります?(こちらではそれでいけたんですが... こうしたらどうでしょう?(変わらないかなぁ?? myBus = new MidiBus(); myBus.addInput(2); myBus.addOutput(5); myBus.registerParent(this); これも試してみてください。 myBus = new MidiBus(new java.lang.Object(), 2, 5); myBus.registerParent(this); あとは別クラスにするくらいしか手がないですがそれでいけるかなぁ?
laclac

2024/08/16 00:40

いずれのコードも、書き換えて実行するとエラーメッセージはなくなりました。しかし、インプットデバイスとアウトプットデバイスの標準出力しかされません。
laclac

2024/08/16 00:41

別クラスにするとはどのような意味でしょうか?
TN8001

2024/08/16 01:42

> いずれのコードも、書き換えて実行するとエラーメッセージはなくなりました。 そうですかよかったです。 > しかし、インプットデバイスとアウトプットデバイスの標準出力しかされません。 println("Note On:"); とかが出ていないという意味ですね? ドラム叩いています? 提示コードでは1秒おきくらいに音が出ますが、それでnoteOn等が呼ばれるわけではありません。 接続しているMIDI機器を操作してください。 それでもダメなら「addInput(2);」の2をほかの番号で試してください。 > 別クラスにするとはどのような意味でしょうか? 回答に追記したようにthisの代わりになるクラスを作ったんですが、上記(TN8001 2024/08/16 00:30)で解決なら気にしないで結構です。
laclac

2024/08/16 03:13

>println("Note On:"); とかが出ていないという意味ですね? はい。そういう意味です。 >ドラム叩いています? 提示コードでは1秒おきくらいに音が出ますが、それでnoteOn等が呼ばれるわけではありません。 接続しているMIDI機器を操作してください。 それでもダメなら「addInput(2);」の2をほかの番号で試してください 叩いています。しかし、addInput(2);の2をほかの番号にしてもnoteOn関数内が呼ばれません。 addOutputの番号は無関係なのですか?いまいちMIDIのINとOUTの区別ができていません。
TN8001

2024/08/16 03:43 編集

> 叩いています。しかし、addInput(2);の2をほかの番号にしてもnoteOn関数内が呼ばれません。 うーーん。。。 Pocket MIDIのInputPortとおなじものならいけると思うんですけどねぇ。 > addOutputの番号は無関係なのですか?いまいちMIDIのINとOUTの区別ができていません。 addOutputは「myBus.sendNoteOn」で出力する先です。 普通は音源("Microsoft MIDI Mapper"とか"Microsoft GS Wavetable Synth"とか外部音源があるならそれ)にします。 --- あと他サイトの話ですが3.5.4はここです。 [Releases / Processing.org](https://processing.org/releases)
laclac

2024/08/16 05:32 編集

ダウンロード先のリンクの添付誠にありがとうございます。 processing3.4.5で実行してみたところ、noteOn関数内が呼ばれました。 もし大学側がprocessing3.4.5の使用をの許可がありましたらこの形態でプログラムを作ります。
TN8001

2024/08/16 05:52

> processing3.4.5で実行してみたところ、noteOn関数内が呼ばれました。 あぁそうですか!!(3.5.4です) 意外でした。「new MidiBus(this」と書けるようになるだけで、「registerParent(this)」と意味は同じはずと思っていました。 仮想デバイスと実機で何か差があるんでしょうかねぇ?? > もし大学側がprocessing3.4.5の使用をの許可がありましたらこの形態でプログラムを作ります。 はい。許可が下りることを祈ります^^;
laclac

2024/08/16 06:39

許可が下りました! 私の質問に多くの時間をかけて下さり、誠にありがとうございました。 発表に向けて、引き続きプログラムを制作していきます。
TN8001

2024/08/16 10:11 編集

> 許可が下りました! いやーよかったですね^^ > 私の質問に多くの時間をかけて下さり、誠にありがとうございました。 解決でよろしいですか? [ヘルプ|質問を解決済みにしたい](https://teratail.com/help#resolve-question) 2.・3.についてもう少し解説が欲しいということなら後で追記しま~~すが~~ した。 > 発表に向けて、引き続きプログラムを制作していきます。 はい。また何かあればお気軽に質問してください。 ただ複数サイトに同時にあげるとごちゃごちゃしますので、反応を見ながら検討してください(laclacさんも大変だったのでは?^^;
guest

あなたの回答

tips

太字

斜体

打ち消し線

見出し

引用テキストの挿入

コードの挿入

リンクの挿入

リストの挿入

番号リストの挿入

表の挿入

水平線の挿入

プレビュー

まだベストアンサーが選ばれていません

会員登録して回答してみよう

アカウントをお持ちの方は

15分調べてもわからないことは
teratailで質問しよう!

ただいまの回答率
85.37%

質問をまとめることで
思考を整理して素早く解決

テンプレート機能で
簡単に質問をまとめる

質問する

関連した質問