我有一个简单的MIDI程序,当你点击那个音符时会弹奏一个音符。但是,单击音符和音符播放之间会有短暂的暂停。我知道延迟是因为我必须打开音序器,添加音符开启和关闭事件,然后播放它。
我的问题是:有没有办法消除滞后?或者至少减少它?我想不出任何办法。提前致谢!代码发布在下面。
import java.awt.*;
import java.awt.event.*;
import javax.sound.midi.*;
import javax.swing.*;
import java.io.IOException;
import javax.imageio.ImageIO;
public class HandyKeyboard {
private JFrame mainFrame;
private JButton lowCKey;
private JButton dKey;
private JButton eKey;
private JButton fKey;
private JButton gKey;
private JButton aKey;
private JButton bKey;
private JButton highCKey;
private JLabel title;
private ContentPanel contentPanel;
public static void main(String[] args){
HandyKeyboard keyboardApp = new HandyKeyboard();
keyboardApp.go();
}
public void go(){
mainFrame = new JFrame("Handy Keyboard");
lowCKey = new JButton("C");
dKey = new JButton("D");
eKey = new JButton("E");
fKey = new JButton("F");
gKey = new JButton("G");
aKey = new JButton("A");
bKey = new JButton("B");
highCKey = new JButton("C");
contentPanel = new ContentPanel("pianoKeysBG.png");
lowCKey.addActionListener(new NoteListener(60));
dKey.addActionListener(new NoteListener(62));
eKey.addActionListener(new NoteListener(64));
fKey.addActionListener(new NoteListener(65));
gKey.addActionListener(new NoteListener(67));
aKey.addActionListener(new NoteListener(69));
bKey.addActionListener(new NoteListener(71));
highCKey.addActionListener(new NoteListener(72));
title = new JLabel("Options");
Font largeFont = new Font("Times New Roman", Font.BOLD, 30);
title.setFont(largeFont);
contentPanel.add(lowCKey);
contentPanel.add(dKey);
contentPanel.add(eKey);
contentPanel.add(fKey);
contentPanel.add(gKey);
contentPanel.add(aKey);
contentPanel.add(bKey);
contentPanel.add(highCKey);
mainFrame.setContentPane(contentPanel);
mainFrame.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
mainFrame.setSize(400, 400);
mainFrame.setVisible(true);
}
private class ContentPanel extends JPanel {
private final Image backgroundImg;
public ContentPanel(String imgURL) {
Image backgroundPic = null;
try {backgroundPic = ImageIO.read(this.getClass().getResource(imgURL));}catch(IOException ex){ex.printStackTrace();}
Image improvedPic = backgroundPic.getScaledInstance(385, 180, Image.SCALE_SMOOTH);
this.backgroundImg = improvedPic;
}
protected void paintComponent(Graphics g){
super.paintComponent(g);
g.drawImage(backgroundImg, 0, 0, 400, 400, this);
}
}
private class NoteListener implements ActionListener {
private int noteInt;
private Sequencer player;
private Sequence seq;
private Track track;
public NoteListener(int i) {
this.noteInt = i;
try {
player = MidiSystem.getSequencer();
player.addMetaEventListener(new MetaEventListener() {
@Override
public void meta(MetaMessage metaMsg) {
if (metaMsg.getType() == 0x2F) {
player.close();
}
}
});
seq = new Sequence(Sequence.PPQ, 1);
track = seq.createTrack();
}
catch (MidiUnavailableException | InvalidMidiDataException e){
e.printStackTrace();
}
}
public void actionPerformed(ActionEvent e) {
try {
player.open();
MidiEvent noteOn = new MidiEvent(new ShortMessage(144, 1, noteInt, 100), 1);
track.add(noteOn);
MidiEvent noteOff = new MidiEvent(new ShortMessage(128, 1, noteInt, 100), 2);
track.add(noteOff);
player.setSequence(seq);
player.setTempoInBPM(80);
player.start();
}
catch (Exception ex) {
ex.printStackTrace();
}
}
}
}