在 java 中更改 MIDI 音量
changing midi volume in java
首先,改变音量是有效的,但我在改变音量时遇到了一些问题,所以 1) 在改变音量后,比如将其设置为 0(无音量),您仍然可以听到歌曲的部分默认值音量 2)歌曲改变音量后恢复到默认音量值
public static void setVolume(double value) {
System.out.println();
int CHANGE_VOLUME = 7;
midivol =(value);
try {
if (synthesizer.getDefaultSoundbank() == null) {
System.out.println(444);
ShortMessage volumeMessage = new ShortMessage();
for (int i = 0; i < 16; i++) {
volumeMessage.setMessage(ShortMessage.CONTROL_CHANGE, i, CHANGE_VOLUME,(int)(value * 127.0));
volumeMessage.setMessage(ShortMessage.CONTROL_CHANGE, i, 39, (int)(value * 127.0));
MidiSystem.getReceiver().send(volumeMessage, -1);
}
} else {
MidiChannel[] channels = synthesizer.getChannels();
for( int c = 0; c < channels.length; c++ ) {
if(channels[c] != null) channels[c].controlChange( 7, (int)( value*127.0) );
}
}
music.setSequence(sequence);
} catch (Exception e) {
e.printStackTrace();
}
}
正在播放 midi:
private void playMidi(String location) {
double gain =Slider.musicvolume;
music = null;
//synthesizer = null;
sequence = null;
File midiFile = new File(location);
try {
sequence = MidiSystem.getSequence(midiFile);
music = MidiSystem.getSequencer(false);
music.open();
music.setSequence(sequence);
} catch (Exception e) {
System.err.println("Problem loading MIDI file.");
e.printStackTrace();
return;
}
if (music instanceof Synthesizer) {
synthesizer = (Synthesizer) music;
} else {
try {
synthesizer = MidiSystem.getSynthesizer();
synthesizer.open();
if (synthesizer.getDefaultSoundbank() == null) {
music.getTransmitter().setReceiver(MidiSystem.getReceiver());
} else {
music.getTransmitter().setReceiver(synthesizer.getReceiver());
}
} catch (Exception e) {
e.printStackTrace();
return;
}
}
MidiChannel[] channels = synthesizer.getChannels();
for (int i = 0; i < channels.length; i++) {
channels[i].controlChange(7, (int) (gain * 127.0));
}
try {
music.setSequence(sequence);
} catch (InvalidMidiDataException e) {
// TODO Auto-generated catch block
e.printStackTrace();
}
music.setLoopCount(Sequencer.LOOP_CONTINUOUSLY);
music.start();
}
volumeMessage.setMessage(ShortMessage.CONTROL_CHANGE, i, CHANGE_VOLUME,(int)(value * 127.0));
volumeMessage.setMessage(ShortMessage.CONTROL_CHANGE, i, 39, (int)(value * 127.0));
MidiSystem.getReceiver().send(volumeMessage, -1);
此代码发送一条消息。该消息的内容是由第二个 setMessage
调用设置的值,因此音量 MSB 根本没有改变。
(这是计算 LSB 的错误方法。)
控制器 7 确实是用于音量,但对于如何解释这些值并没有确切的标准。显然,您的合成器在收到零音量时不会自行静音。
许多 MIDI 文件对控制器 7 进行了自己的更改。如果您的合成器支持 Master Volume,您应该发送它。
首先,改变音量是有效的,但我在改变音量时遇到了一些问题,所以 1) 在改变音量后,比如将其设置为 0(无音量),您仍然可以听到歌曲的部分默认值音量 2)歌曲改变音量后恢复到默认音量值
public static void setVolume(double value) {
System.out.println();
int CHANGE_VOLUME = 7;
midivol =(value);
try {
if (synthesizer.getDefaultSoundbank() == null) {
System.out.println(444);
ShortMessage volumeMessage = new ShortMessage();
for (int i = 0; i < 16; i++) {
volumeMessage.setMessage(ShortMessage.CONTROL_CHANGE, i, CHANGE_VOLUME,(int)(value * 127.0));
volumeMessage.setMessage(ShortMessage.CONTROL_CHANGE, i, 39, (int)(value * 127.0));
MidiSystem.getReceiver().send(volumeMessage, -1);
}
} else {
MidiChannel[] channels = synthesizer.getChannels();
for( int c = 0; c < channels.length; c++ ) {
if(channels[c] != null) channels[c].controlChange( 7, (int)( value*127.0) );
}
}
music.setSequence(sequence);
} catch (Exception e) {
e.printStackTrace();
}
}
正在播放 midi:
private void playMidi(String location) {
double gain =Slider.musicvolume;
music = null;
//synthesizer = null;
sequence = null;
File midiFile = new File(location);
try {
sequence = MidiSystem.getSequence(midiFile);
music = MidiSystem.getSequencer(false);
music.open();
music.setSequence(sequence);
} catch (Exception e) {
System.err.println("Problem loading MIDI file.");
e.printStackTrace();
return;
}
if (music instanceof Synthesizer) {
synthesizer = (Synthesizer) music;
} else {
try {
synthesizer = MidiSystem.getSynthesizer();
synthesizer.open();
if (synthesizer.getDefaultSoundbank() == null) {
music.getTransmitter().setReceiver(MidiSystem.getReceiver());
} else {
music.getTransmitter().setReceiver(synthesizer.getReceiver());
}
} catch (Exception e) {
e.printStackTrace();
return;
}
}
MidiChannel[] channels = synthesizer.getChannels();
for (int i = 0; i < channels.length; i++) {
channels[i].controlChange(7, (int) (gain * 127.0));
}
try {
music.setSequence(sequence);
} catch (InvalidMidiDataException e) {
// TODO Auto-generated catch block
e.printStackTrace();
}
music.setLoopCount(Sequencer.LOOP_CONTINUOUSLY);
music.start();
}
volumeMessage.setMessage(ShortMessage.CONTROL_CHANGE, i, CHANGE_VOLUME,(int)(value * 127.0));
volumeMessage.setMessage(ShortMessage.CONTROL_CHANGE, i, 39, (int)(value * 127.0));
MidiSystem.getReceiver().send(volumeMessage, -1);
此代码发送一条消息。该消息的内容是由第二个 setMessage
调用设置的值,因此音量 MSB 根本没有改变。
(这是计算 LSB 的错误方法。)
控制器 7 确实是用于音量,但对于如何解释这些值并没有确切的标准。显然,您的合成器在收到零音量时不会自行静音。
许多 MIDI 文件对控制器 7 进行了自己的更改。如果您的合成器支持 Master Volume,您应该发送它。