From: Akiyoshi Kamide
Date: Sun, 26 Mar 2017 16:06:44 +0000 (+0900)
Subject: ・シーケンサを閉じてしまった場合の挙動を改善
X-Git-Url: http://git.osdn.net/view?a=commitdiff_plain;h=7382f7045472fe630b16bbef44c4ab745c1078ef;p=midichordhelper%2FMIDIChordHelper.git
・シーケンサを閉じてしまった場合の挙動を改善
・リファクタリング
---
diff --git a/src/camidion/chordhelper/ChordHelperApplet.java b/src/camidion/chordhelper/ChordHelperApplet.java
index 93b2eac..74d0521 100644
--- a/src/camidion/chordhelper/ChordHelperApplet.java
+++ b/src/camidion/chordhelper/ChordHelperApplet.java
@@ -86,10 +86,11 @@ public class ChordHelperApplet extends JApplet {
return playlistModel.getSequenceModelList().stream().anyMatch(m -> m.isModified());
}
/**
- * æå®ãããå°ç¯æ°ã®æ²ããä¹±æ°ã§èªåä½æ²ãã¦ãã¬ã¤ãªã¹ãã¸è¿½å ãã¾ãã
+ * æå®ãããå°ç¯æ°ã®æ²ããä¹±æ°ã§èªåä½æ²ãã¦ãã¬ã¤ãªã¹ãã¸è¿½å ããåçãã¾ãã
* @param measureLength å°ç¯æ°
* @return 追å å
ã®ã¤ã³ããã¯ã¹å¤ï¼ï¼ããå§ã¾ãï¼ã追å ã§ããªãã£ãã¨ã㯠-1
* @throws InvalidMidiDataException {@link Sequencer#setSequence(Sequence)} ãåç
§
+ * @throws IllegalStateException MIDIã·ã¼ã±ã³ãµããã¤ã¹ãéãã¦ããå ´å
*/
public int addRandomSongToPlaylist(int measureLength) throws InvalidMidiDataException {
NewSequenceDialog d = midiEditor.newSequenceDialog;
@@ -144,6 +145,7 @@ public class ChordHelperApplet extends JApplet {
* ãã¬ã¤ãªã¹ãä¸ã§ç¾å¨é¸æããã¦ããMIDIã·ã¼ã±ã³ã¹ãã
* ã·ã¼ã±ã³ãµã¸ãã¼ããã¦åçãã¾ãã
* @throws InvalidMidiDataException {@link Sequencer#setSequence(Sequence)} ãåç
§
+ * @throws IllegalStateException MIDIã·ã¼ã±ã³ãµããã¤ã¹ãéãã¦ããå ´å
*/
public void play() throws InvalidMidiDataException {
play(playlistModel.sequenceListSelectionModel.getMinSelectionIndex());
@@ -153,6 +155,7 @@ public class ChordHelperApplet extends JApplet {
* ã·ã¼ã±ã³ãµã¸ãã¼ããã¦åçãã¾ãã
* @param index ã¤ã³ããã¯ã¹å¤ï¼ï¼ããå§ã¾ãï¼
* @throws InvalidMidiDataException {@link Sequencer#setSequence(Sequence)} ãåç
§
+ * @throws IllegalStateException MIDIã·ã¼ã±ã³ãµããã¤ã¹ãéãã¦ããå ´å
*/
public void play(int index) throws InvalidMidiDataException {
playlistModel.loadToSequencer(index); sequencerModel.start();
@@ -271,7 +274,7 @@ public class ChordHelperApplet extends JApplet {
*/
public static class VersionInfo {
public static final String NAME = "MIDI Chord Helper";
- public static final String VERSION = "Ver.20170324.1";
+ public static final String VERSION = "Ver.20170326.1";
public static final String COPYRIGHT = "Copyright (C) 2004-2017";
public static final String AUTHER = "ï¼ ããã - Akiyoshi Kamide";
public static final String URL = "http://www.yk.rim.or.jp/~kamide/music/chordhelper/";
@@ -382,7 +385,8 @@ public class ChordHelperApplet extends JApplet {
midiDeviceDialog.setIconImage(iconImage);
//
// MIDIã¨ãã£ã¿ãã¤ã¢ãã°ã®æ§ç¯
- (midiEditor = new MidiSequenceEditorDialog(playlistModel, guiMidiDevice)).setIconImage(iconImage);
+ midiEditor = new MidiSequenceEditorDialog(playlistModel, guiMidiDevice, midiDeviceDialog.getOpenAction());
+ midiEditor.setIconImage(iconImage);
//
// ã¡ã¤ã³ç»é¢ã¸ã®MIDIãã¡ã¤ã«ã®ãã©ãã°ï¼ããããåä»éå§
setTransferHandler(midiEditor.transferHandler);
@@ -416,21 +420,21 @@ public class ChordHelperApplet extends JApplet {
//ã·ã¼ã±ã³ãµã¼ã®æéã¹ã©ã¤ãã¼ã®å¤ãå¤ãã£ãã¨ãã®ãªã¹ãã¼ãç»é²
JLabel songTitleLabel = new JLabel();
sequencerModel.addChangeListener(e->{
- SequenceTrackListTableModel sequenceTableModel = sequencerModel.getSequenceTrackListTableModel();
+ SequenceTrackListTableModel sequenceTrackListTableModel = sequencerModel.getSequenceTrackListTableModel();
int loadedSequenceIndex = playlistModel.indexOfSequenceOnSequencer();
songTitleLabel.setText(""+(
loadedSequenceIndex < 0 ? "[No MIDI file loaded]" :
"MIDI file " + loadedSequenceIndex + ": " + (
- sequenceTableModel == null ||
- sequenceTableModel.toString().isEmpty() ?
+ sequenceTrackListTableModel == null ||
+ sequenceTrackListTableModel.toString().isEmpty() ?
"[Untitled]" :
- ""+sequenceTableModel+""
+ ""+sequenceTrackListTableModel+""
)
)+"");
Sequencer sequencer = sequencerModel.getSequencer();
chordMatrix.setPlaying(sequencer.isRunning());
- if( sequenceTableModel != null ) {
- SequenceTickIndex tickIndex = sequenceTableModel.getSequenceTickIndex();
+ if( sequenceTrackListTableModel != null ) {
+ SequenceTickIndex tickIndex = sequenceTrackListTableModel.getSequenceTickIndex();
long tickPos = sequencer.getTickPosition();
tickIndex.tickToMeasure(tickPos);
chordMatrix.setBeat(tickIndex);
@@ -587,7 +591,7 @@ public class ChordHelperApplet extends JApplet {
addToPlaylist(midiUrl);
try {
play();
- } catch (InvalidMidiDataException ex) {
+ } catch (Exception ex) {
ex.printStackTrace();
}
}
diff --git a/src/camidion/chordhelper/mididevice/MidiDeviceModel.java b/src/camidion/chordhelper/mididevice/MidiDeviceModel.java
index e0e89a4..a5ed1ba 100644
--- a/src/camidion/chordhelper/mididevice/MidiDeviceModel.java
+++ b/src/camidion/chordhelper/mididevice/MidiDeviceModel.java
@@ -93,7 +93,7 @@ public class MidiDeviceModel {
* ããããå
¨ã¦éãã¾ãã
*/
public void close() {
- if( rxListModel != null ) rxListModel.closeTransmitters();
+ if( rxListModel != null ) rxListModel.closeAllConnectedTransmitters();
device.close();
}
}
diff --git a/src/camidion/chordhelper/mididevice/MidiDeviceTreeModel.java b/src/camidion/chordhelper/mididevice/MidiDeviceTreeModel.java
index ec2729f..aa4dd89 100644
--- a/src/camidion/chordhelper/mididevice/MidiDeviceTreeModel.java
+++ b/src/camidion/chordhelper/mididevice/MidiDeviceTreeModel.java
@@ -260,8 +260,9 @@ public class MidiDeviceTreeModel extends AbstractList implement
deviceModelList.stream().forEach(m -> {
ReceiverListModel rxListModel = m.getReceiverListModel();
if( rxListModel == null ) return;
- Collection txDeviceModels = rxListModel.closeTransmitters();
- if( ! txDeviceModels.isEmpty() ) rxToTxConnections.put(m, txDeviceModels);
+ Collection txDeviceModels = rxListModel.closeAllConnectedTransmitters();
+ if( txDeviceModels.isEmpty() ) return;
+ rxToTxConnections.put(m, txDeviceModels);
});
return rxToTxConnections;
}
diff --git a/src/camidion/chordhelper/mididevice/MidiSequencerModel.java b/src/camidion/chordhelper/mididevice/MidiSequencerModel.java
index de0050c..75911f5 100644
--- a/src/camidion/chordhelper/mididevice/MidiSequencerModel.java
+++ b/src/camidion/chordhelper/mididevice/MidiSequencerModel.java
@@ -5,6 +5,7 @@ import java.util.HashMap;
import java.util.Map;
import javax.sound.midi.InvalidMidiDataException;
+import javax.sound.midi.MidiUnavailableException;
import javax.sound.midi.Sequence;
import javax.sound.midi.Sequencer;
import javax.swing.AbstractAction;
@@ -48,8 +49,8 @@ public class MidiSequencerModel extends MidiDeviceModel implements BoundedRangeM
addChangeListener(e->getSequencer().setTempoFactor(SequencerSpeedSlider.tempoFactorOf(getValue())));
}};
/**
- * MIDIã·ã¼ã±ã³ãµãè¿ãã¾ãã
- * @return MIDIã·ã¼ã±ã³ãµ
+ * 対象MIDIã·ã¼ã±ã³ãµããã¤ã¹ï¼{@link #getMidiDevice()}ããã£ã¹ãããçµæï¼ãè¿ãã¾ãã
+ * @return 対象MIDIã·ã¼ã±ã³ãµããã¤ã¹
*/
public Sequencer getSequencer() { return (Sequencer)device; }
/**
@@ -67,57 +68,100 @@ public class MidiSequencerModel extends MidiDeviceModel implements BoundedRangeM
{
putValue(SHORT_DESCRIPTION, "Start/Stop recording or playing - é²é³ã¾ãã¯åçã®éå§ï¼åæ¢");
setRunning(false);
+ updateEnableStatus();
}
@Override
public void actionPerformed(ActionEvent event) {
- if(timeRangeUpdater.isRunning()) stop(); else start();
+ if( timeRangeUpdater.isRunning() ) stop(); else start();
+ updateEnableStatus();
}
private void setRunning(boolean isRunning) {
putValue(LARGE_ICON_KEY, iconMap.get(isRunning));
putValue(SELECTED_KEY, isRunning);
}
+ /**
+ * åçã¾ãã¯é²é³ãå¯è½ããã§ãã¯ããæä½å¯è½ç¶æ
ãæ´æ°ãã¾ãã
+ */
+ public void updateEnableStatus() { setEnabled(isStartable()); }
}
/**
- * ãã®ã¢ãã«ã®MIDIã·ã¼ã±ã³ãµãéå§ãã¾ãã
+ * åçã¾ãã¯é²é³ãå¯è½ã調ã¹ã¾ãã
+ * 以ä¸ã®æ¡ä»¶ãæã£ãã¨ãã«åçã¾ãã¯é²é³ãå¯è½ã¨å¤å®ããã¾ãã
+ *
+ * - MIDIã·ã¼ã±ã³ãµããã¤ã¹ãéãã¦ãã
+ * - MIDIã·ã¼ã±ã³ãµã«æä½å¯¾è±¡ã®MIDIã·ã¼ã±ã³ã¹ãè¨å®ããã¦ãã
+ *
+ * @return åçã¾ãã¯é²é³ãå¯è½ãªå ´åtrue
+ */
+ public boolean isStartable() {
+ return device.isOpen() && getSequencer().getSequence() != null;
+ }
+ /**
+ * {@inheritDoc}
+ * ã·ã¼ã±ã³ãµã¢ãã«ã®å ´åãé²é³åçå¯è½ç¶æ
ãå¤ããã®ã§ãéå§çµäºã¢ã¯ã·ã§ã³ã«ãéç¥ãã¾ãã
+ */
+ @Override
+ public void open() throws MidiUnavailableException {
+ super.open();
+ startStopAction.updateEnableStatus();
+ fireStateChanged();
+ if( sequenceTrackListTableModel != null ) {
+ sequenceTrackListTableModel.getParent().fireTableDataChanged();
+ }
+ }
+ /**
+ * {@inheritDoc}
+ * ã·ã¼ã±ã³ãµã¢ãã«ã®å ´åãåçã¾ãã¯é²é³ãä¸å¯è½ã«ãªãã®ã§ãéå§çµäºã¢ã¯ã·ã§ã³ã«ãéç¥ãã¾ãã
+ */
+ @Override
+ public void close() {
+ stop();
+ try {
+ setSequenceTrackListTableModel(null);
+ } catch (InvalidMidiDataException|IllegalStateException e) {
+ e.printStackTrace();
+ }
+ super.close();
+ startStopAction.updateEnableStatus();
+ fireStateChanged();
+ if( sequenceTrackListTableModel != null ) {
+ sequenceTrackListTableModel.getParent().fireTableDataChanged();
+ }
+ }
+ /**
+ * åçã¾ãã¯é²é³ãéå§ãã¾ãã
*
* é²é³ããMIDIãã£ã³ãã«ãMIDIã¨ãã£ã¿ã§æå®ããã¦ããå ´åã
- * é²é³ã¹ã¿ã¼ãæã®ã¿ã¤ã ã¹ã¿ã³ããæ£ããï¼ã«ãªãããã
- * åMIDIããã¤ã¹ã®ã¿ã¤ã ã¹ã¿ã³ãããã¹ã¦ãªã»ãããã¾ãã
+ * é²é³ã¹ã¿ã¼ãæã®ã¿ã¤ã ã¹ã¿ã³ããæ£ããï¼ã«ãªããããåMIDIããã¤ã¹ã®ã¿ã¤ã ã¹ã¿ã³ãããã¹ã¦ãªã»ãããã¾ãã
*
+ * ãã®ã·ã¼ã±ã³ãµã®MIDIããã¤ã¹ãéãã¦ããå ´åãåçãé²é³ã¯éå§ããã¾ããã
*/
public void start() {
+ if( ! device.isOpen() ) return;
Sequencer sequencer = getSequencer();
- if( ! sequencer.isOpen() || sequencer.getSequence() == null ) {
- timeRangeUpdater.stop();
- startStopAction.setRunning(false);
- return;
- }
- startStopAction.setRunning(true);
- timeRangeUpdater.start();
- SequenceTrackListTableModel sequenceTableModel = getSequenceTrackListTableModel();
- if( sequenceTableModel != null && sequenceTableModel.hasRecordChannel() ) {
+ SequenceTrackListTableModel sequenceTrackListTableModel = getSequenceTrackListTableModel();
+ if( sequenceTrackListTableModel != null && sequenceTrackListTableModel.hasRecordChannel() ) {
deviceTreeModel.resetMicrosecondPosition();
- System.gc();
sequencer.startRecording();
- }
- else {
- System.gc();
- sequencer.start();
- }
+ } else sequencer.start();
+ timeRangeUpdater.start();
+ startStopAction.setRunning(true);
fireStateChanged();
}
/**
- * ãã®ã¢ãã«ã®MIDIã·ã¼ã±ã³ãµãåæ¢ãã¾ãã
+ * åçã¾ãã¯é²é³ãåæ¢ãã¾ãã
*/
public void stop() {
Sequencer sequencer = getSequencer();
- if(sequencer.isOpen()) sequencer.stop();
+ if( sequencer.isOpen() ) sequencer.stop();
timeRangeUpdater.stop();
startStopAction.setRunning(false);
fireStateChanged();
}
/**
- * {@link Sequencer#getMicrosecondLength()} ã¨åãã§ãã
+ * ãã®ã·ã¼ã±ã³ãµã¼ã«ãã¼ãããã¦ããã·ã¼ã±ã³ã¹ã®é·ãããã¤ã¯ãç§åä½ã§è¿ãã¾ãã
+ * ã·ã¼ã±ã³ã¹ãè¨å®ããã¦ããªãå ´åã¯0ãè¿ãã¾ãã
+ * æ²ãé·ãã㦠{@link Sequencer#getMicrosecondLength()} ãè² æ°ãè¿ãã¦ãã¾ã£ãå ´åã®è£æ£ãè¡ãã¾ãã
* @return ãã¤ã¯ãç§åä½ã§ã®ã·ã¼ã±ã³ã¹ã®é·ã
*/
public long getMicrosecondLength() {
@@ -129,6 +173,15 @@ public class MidiSequencerModel extends MidiDeviceModel implements BoundedRangeM
long usLength = getSequencer().getMicrosecondLength();
return usLength < 0 ? 0x100000000L + usLength : usLength ;
}
+ /**
+ * ã·ã¼ã±ã³ã¹ä¸ã®ç¾å¨ä½ç½®ããã¤ã¯ãç§åä½ã§è¿ãã¾ãã
+ * æ²ãé·ãã㦠{@link Sequencer#getMicrosecondPosition()} ãè² æ°ãè¿ãã¦ãã¾ã£ãå ´åã®è£æ£ãè¡ãã¾ãã
+ * @return ãã¤ã¯ãç§åä½ã§ã®ç¾å¨ã®ä½ç½®
+ */
+ public long getMicrosecondPosition() {
+ long usPosition = getSequencer().getMicrosecondPosition();
+ return usPosition < 0 ? 0x100000000L + usPosition : usPosition ;
+ }
@Override
public int getMaximum() { return (int)(getMicrosecondLength()/RESOLUTION_MICROSECOND); }
@Override
@@ -141,14 +194,6 @@ public class MidiSequencerModel extends MidiDeviceModel implements BoundedRangeM
public int getExtent() { return 0; }
@Override
public void setExtent(int newExtent) {}
- /**
- * {@link Sequencer#getMicrosecondPosition()} ã¨åãã§ãã
- * @return ãã¤ã¯ãç§åä½ã§ã®ç¾å¨ã®ä½ç½®
- */
- public long getMicrosecondPosition() {
- long usPosition = getSequencer().getMicrosecondPosition();
- return usPosition < 0 ? 0x100000000L + usPosition : usPosition ;
- }
@Override
public int getValue() { return (int)(getMicrosecondPosition()/RESOLUTION_MICROSECOND); }
@Override
@@ -171,8 +216,7 @@ public class MidiSequencerModel extends MidiDeviceModel implements BoundedRangeM
*/
private javax.swing.Timer timeRangeUpdater = new javax.swing.Timer(20, e->{
if( valueIsAdjusting || ! getSequencer().isRunning() ) {
- // æåã§ç§»åä¸ã®å ´åããã·ã¼ã±ã³ãµãæ¢ã¾ã£ã¦ããå ´åã¯ã
- // ã¿ã¤ãã¼ã«ããæ´æ°ã¯ä¸è¦
+ // æåã§ç§»åä¸ã®å ´åããã·ã¼ã±ã³ãµãæ¢ã¾ã£ã¦ããå ´åã¯ãã¿ã¤ãã¼ã«ããæ´æ°ã¯ä¸è¦
return;
}
// ãªã¹ãã¼ã«èªã¿è¾¼ã¿ãä¿ã
@@ -223,35 +267,31 @@ public class MidiSequencerModel extends MidiDeviceModel implements BoundedRangeM
/**
* MIDIãã©ãã¯ãªã¹ããã¼ãã«ã¢ãã«
*/
- private SequenceTrackListTableModel sequenceTableModel = null;
+ private SequenceTrackListTableModel sequenceTrackListTableModel = null;
/**
* ãã®ã·ã¼ã±ã³ãµã¼ã«ç¾å¨ãã¼ãããã¦ããã·ã¼ã±ã³ã¹ã®MIDIãã©ãã¯ãªã¹ããã¼ãã«ã¢ãã«ãè¿ãã¾ãã
* @return MIDIãã©ãã¯ãªã¹ããã¼ãã«ã¢ãã«ï¼ä½ããã¼ãããã¦ããªããã°nullï¼
*/
public SequenceTrackListTableModel getSequenceTrackListTableModel() {
- return sequenceTableModel;
+ return sequenceTrackListTableModel;
}
/**
* MIDIãã©ãã¯ãªã¹ããã¼ãã«ã¢ãã«ããã®ã·ã¼ã±ã³ãµã¼ã¢ãã«ã«ã»ãããã¾ãã
* nullãæå®ãã¦ã¢ã³ã»ãããããã¨ãã§ãã¾ãã
* @param sequenceTableModel MIDIãã©ãã¯ãªã¹ããã¼ãã«ã¢ãã«
* @throws InvalidMidiDataException {@link Sequencer#setSequence(Sequence)} ãåç
§
+ * @throws IllegalStateException MIDIã·ã¼ã±ã³ãµããã¤ã¹ãéãã¦ããç¶æ
ã§å¼æ°ã«nullãæå®ããå ´å
*/
public void setSequenceTrackListTableModel(SequenceTrackListTableModel sequenceTableModel)
throws InvalidMidiDataException
{
- // javax.sound.midi:Sequencer.setSequence() ã®ããã¥ã¡ã³ãã«ãã
- // ããã®ã¡ã½ããã¯ãSequencer ãéãã¦ããå ´åã§ãå¼ã³åºããã¨ãã§ãã¾ãã ã
- // ã¨ããè¨è¿°ã¯ãnull ãã»ããããå ´åã«ã¯å½ã¦ã¯ã¾ããªãã
- // é£éçã« stop() ãå¼ã°ããããã« IllegalStateException sequencer not open ãåºãã
- // ãã®ç¾è±¡ãåé¿ãããããããããããã§ãã¯ãã¦ãã setSequence() ãå¼ã³åºãã¦ããã
- //
- if( sequenceTableModel != null || getSequencer().isOpen() ) {
- getSequencer().setSequence(sequenceTableModel == null ? null : sequenceTableModel.getSequence());
- }
- if( this.sequenceTableModel != null ) this.sequenceTableModel.fireTableDataChanged();
+ Sequencer sequencer = getSequencer();
+ Sequence sequence = sequenceTableModel == null ? null : sequenceTableModel.getSequence();
+ sequencer.setSequence(sequence);
+ startStopAction.updateEnableStatus();
+ if( this.sequenceTrackListTableModel != null ) this.sequenceTrackListTableModel.fireTableDataChanged();
if( sequenceTableModel != null ) sequenceTableModel.fireTableDataChanged();
- this.sequenceTableModel = sequenceTableModel;
+ this.sequenceTrackListTableModel = sequenceTableModel;
fireStateChanged();
}
/**
@@ -259,8 +299,8 @@ public class MidiSequencerModel extends MidiDeviceModel implements BoundedRangeM
* @param measureOffset ä½å°ç¯é²ãããï¼æ»ãããã¨ãã¯è² æ°ãæå®ï¼
*/
private void moveMeasure(int measureOffset) {
- if( measureOffset == 0 || sequenceTableModel == null ) return;
- SequenceTickIndex seqIndex = sequenceTableModel.getSequenceTickIndex();
+ if( measureOffset == 0 || sequenceTrackListTableModel == null ) return;
+ SequenceTickIndex seqIndex = sequenceTrackListTableModel.getSequenceTickIndex();
Sequencer sequencer = getSequencer();
int measurePosition = seqIndex.tickToMeasure(sequencer.getTickPosition());
long newTickPosition = seqIndex.measureToTick(measurePosition + measureOffset);
diff --git a/src/camidion/chordhelper/mididevice/ReceiverListModel.java b/src/camidion/chordhelper/mididevice/ReceiverListModel.java
index 0da6495..c5d15c4 100644
--- a/src/camidion/chordhelper/mididevice/ReceiverListModel.java
+++ b/src/camidion/chordhelper/mididevice/ReceiverListModel.java
@@ -1,8 +1,8 @@
package camidion.chordhelper.mididevice;
-import java.util.LinkedHashSet;
import java.util.List;
import java.util.Set;
+import java.util.stream.Collectors;
import javax.sound.midi.MidiDevice;
import javax.sound.midi.MidiUnavailableException;
@@ -29,21 +29,18 @@ public class ReceiverListModel extends AbstractTransceiverListModel {
* ãã®ãªã¹ãã¢ãã«ã®{@link Receiver}ã«æ¥ç¶ããã{@link Transmitter}ãå
¨ã¦éãã
* æ¥ç¶ç¸æã ã£ãMIDIããã¤ã¹ã¢ãã«ã®ã¦ãã¼ã¯ãªéåãè¿ãã¾ãã
*
- * @return éãã{@link Transmitter}ã®{@link MidiDeviceModel}ã®éå
+ * @return éãã{@link Transmitter}ãæã£ã¦ãã{@link MidiDeviceModel}ã®éå
*/
- public Set closeTransmitters() {
- Set peerDeviceModelSet = new LinkedHashSet<>();
- List rxList = getTransceivers();
- if( ! rxList.isEmpty() ) {
- for( MidiDeviceModel peerDeviceModel : deviceModel.getDeviceTreeModel() ) {
- if( peerDeviceModel == deviceModel ) continue;
- TransmitterListModel txListModel = peerDeviceModel.getTransmitterListModel();
- if( txListModel == null ) continue;
- for( Receiver rx : rxList )
- if( ! txListModel.closeTransmittersFor(rx).isEmpty() )
- peerDeviceModelSet.add(peerDeviceModel);
- }
- }
- return peerDeviceModelSet;
+ public Set closeAllConnectedTransmitters() {
+ List allDeviceModels = deviceModel.getDeviceTreeModel();
+ return allDeviceModels.stream().filter(
+ peer -> peer != deviceModel
+ && peer.getTransmitterListModel() != null
+ && ! getTransceivers().stream()
+ .map(rx -> peer.getTransmitterListModel().closeTransmittersFor(rx))
+ .flatMap(closedTxList -> closedTxList.stream())
+ .collect(Collectors.toSet())
+ .isEmpty()
+ ).collect(Collectors.toSet());
}
}
diff --git a/src/camidion/chordhelper/midieditor/MidiSequenceEditorDialog.java b/src/camidion/chordhelper/midieditor/MidiSequenceEditorDialog.java
index f665c7e..011dfd3 100644
--- a/src/camidion/chordhelper/midieditor/MidiSequenceEditorDialog.java
+++ b/src/camidion/chordhelper/midieditor/MidiSequenceEditorDialog.java
@@ -91,6 +91,7 @@ public class MidiSequenceEditorDialog extends JDialog {
if( isVisible() ) toFront(); else setVisible(true);
}
};
+ private Action midiDeviceDialogOpenAction;
/**
* ã¨ã©ã¼ã¡ãã»ã¼ã¸ãã¤ã¢ãã°ã表示ãã¾ãã
@@ -149,24 +150,28 @@ public class MidiSequenceEditorDialog extends JDialog {
if( firstIndex < 0 ) firstIndex = lastIndex;
} catch(IOException|InvalidMidiDataException e) {
String message = "Could not open as MIDI file "+file+"\n"+e;
- if( ! itr.hasNext() ) { showWarning(message); break; }
+ if( ! itr.hasNext() ) { // No more file to play
+ showWarning(message); break;
+ }
if( ! confirm(message + "\n\nContinue to open next file ?") ) break;
} catch(AccessControlException e) {
showError(e); break;
+ } catch(Exception e) {
+ showError(e); break;
}
}
- MidiSequencerModel sequencerModel = playlist.getSequencerModel();
- if( sequencerModel.getSequencer().isRunning() ) {
- String command = (String)openAction.getValue(Action.NAME);
- openAction.actionPerformed(new ActionEvent(this, ActionEvent.ACTION_PERFORMED, command));
- return;
- }
- if( firstIndex >= 0 ) {
- try {
+ try {
+ MidiSequencerModel sequencerModel = playlist.getSequencerModel();
+ if( sequencerModel.getSequencer().isRunning() ) {
+ String command = (String)openAction.getValue(Action.NAME);
+ openAction.actionPerformed(new ActionEvent(this, ActionEvent.ACTION_PERFORMED, command));
+ return;
+ }
+ if( firstIndex >= 0 ) {
playlist.loadToSequencer(firstIndex);
- } catch (InvalidMidiDataException e) { showError(e); return; }
- sequencerModel.start();
- }
+ sequencerModel.start();
+ }
+ } catch (Exception e) { showError(e); }
}
private static final Insets ZERO_INSETS = new Insets(0,0,0,0);
@@ -274,7 +279,7 @@ public class MidiSequenceEditorDialog extends JDialog {
//
// ã¿ã¤ãã«ã«åè¨ã·ã¼ã±ã³ã¹é·ã表示
if( lengthColumn != null ) {
- int sec = getModel().getTotalTimeInSeconds();
+ int sec = getModel().getSecondLength();
String title = PlaylistTableModel.Column.LENGTH.title;
title = String.format(title+" [%02d:%02d]", sec/60, sec%60);
lengthColumn.setHeaderValue(title);
@@ -286,25 +291,20 @@ public class MidiSequenceEditorDialog extends JDialog {
JTableHeader th = getTableHeader();
if( th != null ) th.repaint();
}
- /**
- * æéä½ç½®è¡¨ç¤ºã»ã«ã¨ãã£ã¿ï¼ããã«ã¯ãªãã¯å°ç¨ï¼
- */
+ /** æéä½ç½®ã表示ããããã«ã¯ãªãã¯ã«ããã·ã¼ã±ã³ãµã¸ã®ãã¼ãã®ã¿ãåãä»ããã»ã«ã¨ãã£ã¿ */
private class PositionCellEditor extends AbstractCellEditor implements TableCellEditor {
public PositionCellEditor() {
- int column = PlaylistTableModel.Column.POSITION.ordinal();
- TableColumn tc = getColumnModel().getColumn(column);
+ TableColumn tc = getColumnModel().getColumn(PlaylistTableModel.Column.POSITION.ordinal());
tc.setCellEditor(this);
}
/**
* ã»ã«ãããã«ã¯ãªãã¯ããã¨ãã ãç·¨éã¢ã¼ãã«å
¥ãããã«ãã¾ãã
* @param e ã¤ãã³ãï¼ãã¦ã¹ã¤ãã³ãï¼
- * @return ç·¨éå¯è½ã«ãªã£ããtrue
+ * @return ç·¨éå¯è½ãªå ´åtrue
*/
@Override
public boolean isCellEditable(EventObject e) {
- // ãã¦ã¹ã¤ãã³ã以å¤ã®ã¤ãã³ãã§ã¯ç·¨éä¸å¯
- if( ! (e instanceof MouseEvent) ) return false;
- return ((MouseEvent)e).getClickCount() == 2;
+ return (e instanceof MouseEvent) && ((MouseEvent)e).getClickCount() == 2;
}
@Override
public Object getCellEditorValue() { return null; }
@@ -320,88 +320,104 @@ public class MidiSequenceEditorDialog extends JDialog {
) {
try {
getModel().loadToSequencer(row);
- } catch (InvalidMidiDataException ex) { showError(ex); }
+ } catch (InvalidMidiDataException|IllegalStateException ex) {
+ showError(ex);
+ }
fireEditingStopped();
return null;
}
}
- /**
- * ãã¬ã¤ãã¿ã³ãåãè¾¼ãã ã»ã«ã¨ãã£ã¿
- */
- private class PlayButtonCellEditor extends AbstractCellEditor
- implements TableCellEditor, TableCellRenderer
- {
- private JToggleButton playButton = new JToggleButton(
- getModel().getSequencerModel().getStartStopAction()
- ) {
+ /** åçãã¿ã³ãåãè¾¼ãã ã»ã«ã®ç·¨éãæç»ãè¡ãã¯ã©ã¹ã§ãã */
+ private class PlayButtonCellEditor extends AbstractCellEditor implements TableCellEditor, TableCellRenderer {
+ /** åãè¾¼ã¿ç¨ã®åçãã¿ã³ */
+ private JToggleButton playButton = new JToggleButton(getModel().getSequencerModel().getStartStopAction()) {
{ setMargin(ZERO_INSETS); }
};
+ /**
+ * åãè¾¼ã¿ç¨ã®MIDIããã¤ã¹æ¥ç¶ãã¿ã³ï¼ãã®ã·ã¼ã±ã³ã¹ããã¼ããã¦ããã·ã¼ã±ã³ãµãéãã¦ããªãã£ãã¨ãã«è¡¨ç¤ºï¼
+ */
+ private JButton midiDeviceConnectionButton = new JButton(midiDeviceDialogOpenAction) {
+ { setMargin(ZERO_INSETS); }
+ };
+ /**
+ * åçãã¿ã³ãåãè¾¼ãã»ã«ã¨ãã£ã¿ãæ§ç¯ããåã«å¯¾ããã¬ã³ãã©ãã¨ãã£ã¿ã¨ãã¦ç»é²ãã¾ãã
+ */
public PlayButtonCellEditor() {
- int column = PlaylistTableModel.Column.PLAY.ordinal();
- TableColumn tc = getColumnModel().getColumn(column);
+ TableColumn tc = getColumnModel().getColumn(PlaylistTableModel.Column.PLAY.ordinal());
tc.setCellRenderer(this);
tc.setCellEditor(this);
}
/**
* {@inheritDoc}
*
- * ãã®å®è£
ã§ã¯ãã¯ãªãã¯ããã»ã«ã®ã·ã¼ã±ã³ã¹ã
- * ã·ã¼ã±ã³ãµã¼ã«ãã¼ãããã¦ããå ´åã«
- * trueãè¿ãã¦ãã¬ã¤ãã¿ã³ãæ¼ããããã«ãã¾ãã
- * ããã§ãªãå ´åã¯ãã¬ã¤ãã¿ã³ã®ãªãã»ã«ãªã®ã§ã
+ *
ãã®å®è£
ã§ã¯ãã¯ãªãã¯ããã»ã«ã®ã·ã¼ã±ã³ã¹ãã·ã¼ã±ã³ãµã¼ã§åçå¯è½ãªå ´åã«
+ * trueãè¿ãã¦åçãã¿ã³ãæ¼ããããã«ãã¾ãã
+ * ãã以å¤ã®ã»ã«ã«ã¤ãã¦ã¯ãæ°ãã«ã·ã¼ã±ã³ãµã¼ã¸ã®ãã¼ããå¯è½ã«ããããã
* ããã«ã¯ãªãã¯ãããã¨ãã ãtrueãè¿ãã¾ãã
*
*/
@Override
public boolean isCellEditable(EventObject e) {
- // ãã¦ã¹ã¤ãã³ã以å¤ã¯ããã©ã«ãã¡ã½ããã«ãä»»ã
+ // ãã¦ã¹ã¤ãã³ãã®ã¿ãåãä»ãããã以å¤ã¯ããã©ã«ãã¨ãã£ã¿ã«æ¯ã
if( ! (e instanceof MouseEvent) ) return super.isCellEditable(e);
+ //
+ // ã¨ãã£ã¿ãç·¨éãçµäºãããã¨ããªã¹ãã¼ã«éç¥
fireEditingStopped();
- MouseEvent me = (MouseEvent)e;
//
- // ã¯ãªãã¯ãããã»ã«ã®è¡ãç¹å®
+ // ã¯ãªãã¯ãããã»ã«ã®è¡ä½ç½®ãææ¡ï¼æ¬å¤ã ã£ããç·¨éä¸å¯ï¼
+ MouseEvent me = (MouseEvent)e;
int row = rowAtPoint(me.getPoint());
if( row < 0 ) return false;
- PlaylistTableModel model = getModel();
- if( row >= model.getRowCount() ) return false;
//
- // ã»ã«å
ã«ãã¬ã¤ãã¿ã³ãããã°ãã·ã³ã°ã«ã¯ãªãã¯ãåãä»ããã
- // ãã¬ã¤ãã¿ã³ã®ãªãã»ã«ã¯ãããã«ã¯ãªãã¯ã®ã¿åãä»ããã
- return model.getSequenceModelList().get(row).isOnSequencer() || me.getClickCount() == 2;
+ // ã·ã¼ã±ã³ãµã¼ã«ãã¼ãæ¸ã¿ã®å ´åã¯ãã·ã³ã°ã«ã¯ãªãã¯ãåãä»ããã
+ // ãã以å¤ã¯ãããã«ã¯ãªãã¯ã®ã¿åãä»ããã
+ PlaylistTableModel model = getModel();
+ boolean isOnSequencer = model.getSequenceModelList().get(row).isOnSequencer();
+ return isOnSequencer || me.getClickCount() == 2;
}
@Override
public Object getCellEditorValue() { return null; }
/**
* {@inheritDoc}
*
- * ãã®å®è£
ã§ã¯ãè¡ã®è¡¨ãã·ã¼ã±ã³ã¹ãã·ã¼ã±ã³ãµã¼ã«ãã¼ãããã¦ããå ´åã«ãã¬ã¤ãã¿ã³ãè¿ãã¾ãã
- * ããã§ãªãå ´åã¯ããã®ã·ã¼ã±ã³ã¹ãã·ã¼ã±ã³ãµã¼ã«ãã¼ããã¦nullãè¿ãã¾ãã
+ *
ãã®å®è£
ã§ã¯ãè¡ã®è¡¨ãã·ã¼ã±ã³ã¹ã®ç¶æ
ã«å¿ãããã¿ã³ã表示ãã¾ãã
+ * ãã以å¤ã®å ´åã¯ãæ°ãã«ãã®ã·ã¼ã±ã³ã¹ãã·ã¼ã±ã³ãµã¼ã«ãã¼ããã¾ããã
+ * 以éã®ç·¨éã¯ä¸å¯ã¨ãã¦nullãè¿ãã¾ãã
*
*/
@Override
public Component getTableCellEditorComponent(
- JTable table, Object value, boolean isSelected, int row, int column
+ JTable table, Object value, boolean isSelected,
+ int row, int column
) {
fireEditingStopped();
PlaylistTableModel model = getModel();
- if( model.getSequenceModelList().get(row).isOnSequencer() ) return playButton;
+ if( model.getSequenceModelList().get(row).isOnSequencer() ) {
+ return model.getSequencerModel().getSequencer().isOpen() ? playButton : midiDeviceConnectionButton;
+ }
try {
model.loadToSequencer(row);
} catch (InvalidMidiDataException ex) { showError(ex); }
return null;
}
+ /**
+ * {@inheritDoc}
+ *
+ * ãã®å®è£
ã§ã¯ãè¡ã®è¡¨ãã·ã¼ã±ã³ã¹ã®ç¶æ
ã«å¿ãããã¿ã³ã表示ãã¾ãã
+ * ãã以å¤ã®å ´åã¯ããã©ã«ãã¬ã³ãã©ã¼ã«æç»ããã¾ãã
+ *
+ */
@Override
public Component getTableCellRendererComponent(
JTable table, Object value, boolean isSelected,
boolean hasFocus, int row, int column
) {
PlaylistTableModel model = getModel();
- if(model.getSequenceModelList().get(row).isOnSequencer()) return playButton;
- Class> cc = model.getColumnClass(column);
- TableCellRenderer defaultRenderer = table.getDefaultRenderer(cc);
- return defaultRenderer.getTableCellRendererComponent(
- table, value, isSelected, hasFocus, row, column
- );
+ if( model.getSequenceModelList().get(row).isOnSequencer() ) {
+ return model.getSequencerModel().getSequencer().isOpen() ? playButton : midiDeviceConnectionButton;
+ }
+ TableCellRenderer defaultRenderer = table.getDefaultRenderer(model.getColumnClass(column));
+ return defaultRenderer.getTableCellRendererComponent(table, value, isSelected, hasFocus, row, column);
}
}
/**
@@ -424,7 +440,8 @@ public class MidiSequenceEditorDialog extends JDialog {
public void actionPerformed(ActionEvent event) {
PlaylistTableModel model = getModel();
if( midiFileChooser != null ) {
- if( model.getSelectedSequenceModel().isModified() ) {
+ SequenceTrackListTableModel seqModel = model.getSelectedSequenceModel();
+ if( seqModel != null && seqModel.isModified() ) {
String message =
"Selected MIDI sequence not saved - delete it ?\n" +
"é¸æããMIDIã·ã¼ã±ã³ã¹ã¯ã¾ã ä¿åããã¦ãã¾ãããåé¤ãã¾ããï¼";
@@ -433,7 +450,7 @@ public class MidiSequenceEditorDialog extends JDialog {
}
try {
model.removeSelectedSequence();
- } catch (InvalidMidiDataException ex) {
+ } catch (InvalidMidiDataException|IllegalStateException ex) {
showError(ex);
}
}
@@ -456,6 +473,7 @@ public class MidiSequenceEditorDialog extends JDialog {
public void actionPerformed(ActionEvent event) {
PlaylistTableModel playlistModel = getModel();
SequenceTrackListTableModel sequenceModel = playlistModel.getSelectedSequenceModel();
+ if( sequenceModel == null ) return;
String fn = sequenceModel.getFilename();
if( fn != null && ! fn.isEmpty() ) setSelectedFile(new File(fn));
if( showSaveDialog((Component)event.getSource()) != JFileChooser.APPROVE_OPTION ) return;
@@ -469,7 +487,7 @@ public class MidiSequenceEditorDialog extends JDialog {
sequenceModel.setModified(false);
playlistModel.fireSequenceModified(sequenceModel, false);
}
- catch( IOException ex ) { showError(ex); }
+ catch( Exception ex ) { showError(ex); }
}
};
/**
@@ -479,8 +497,10 @@ public class MidiSequenceEditorDialog extends JDialog {
{ putValue(Action.SHORT_DESCRIPTION, "Open MIDI file - MIDIãã¡ã¤ã«ãéã"); }
@Override
public void actionPerformed(ActionEvent event) {
- if( showOpenDialog((Component)event.getSource()) != JFileChooser.APPROVE_OPTION ) return;
- play(Arrays.asList(getSelectedFile()));
+ try {
+ if( showOpenDialog((Component)event.getSource()) != JFileChooser.APPROVE_OPTION ) return;
+ play(Arrays.asList(getSelectedFile()));
+ } catch( Exception ex ) { showError(ex); }
}
};
};
@@ -1101,9 +1121,11 @@ public class MidiSequenceEditorDialog extends JDialog {
* æ°ãã {@link MidiSequenceEditorDialog} ãæ§ç¯ãã¾ãã
* @param playlistTableModel ãã®ã¨ãã£ã¿ãåç
§ãããã¬ã¤ãªã¹ãã¢ãã«
* @param outputMidiDevice ã¤ãã³ããã¼ãã«ã®æä½é³åºåå
MIDIããã¤ã¹
+ * @param midiDeviceDialogOpenAction MIDIããã¤ã¹ãã¤ã¢ãã°ãéãã¢ã¯ã·ã§ã³
*/
- public MidiSequenceEditorDialog(PlaylistTableModel playlistTableModel, VirtualMidiDevice outputMidiDevice) {
+ public MidiSequenceEditorDialog(PlaylistTableModel playlistTableModel, VirtualMidiDevice outputMidiDevice, Action midiDeviceDialogOpenAction) {
this.outputMidiDevice = outputMidiDevice;
+ this.midiDeviceDialogOpenAction = midiDeviceDialogOpenAction;
sequenceListTable = new SequenceListTable(playlistTableModel);
trackListTable = new TrackListTable(
new SequenceTrackListTableModel(playlistTableModel, null, null)
diff --git a/src/camidion/chordhelper/midieditor/NewSequenceDialog.java b/src/camidion/chordhelper/midieditor/NewSequenceDialog.java
index a99d19b..7ff2f03 100644
--- a/src/camidion/chordhelper/midieditor/NewSequenceDialog.java
+++ b/src/camidion/chordhelper/midieditor/NewSequenceDialog.java
@@ -17,7 +17,6 @@ import java.awt.event.MouseListener;
import java.util.ArrayList;
import java.util.Vector;
-import javax.sound.midi.InvalidMidiDataException;
import javax.sound.midi.MidiChannel;
import javax.sound.midi.Sequence;
import javax.swing.AbstractAction;
@@ -107,10 +106,9 @@ public class NewSequenceDialog extends JDialog {
public void actionPerformed(ActionEvent event) {
try {
playlist.getSequenceModelList().get(playlist.play(getMidiSequence())).setModified(true);
- } catch (InvalidMidiDataException ex) {
- ex.printStackTrace();
+ } catch (Exception ex) {
JOptionPane.showMessageDialog(
- NewSequenceDialog.this, ex.getMessage(),
+ NewSequenceDialog.this, ex,
ChordHelperApplet.VersionInfo.NAME, JOptionPane.ERROR_MESSAGE);
}
setVisible(false);
diff --git a/src/camidion/chordhelper/midieditor/PlaylistTableModel.java b/src/camidion/chordhelper/midieditor/PlaylistTableModel.java
index fb495fe..6f2e411 100644
--- a/src/camidion/chordhelper/midieditor/PlaylistTableModel.java
+++ b/src/camidion/chordhelper/midieditor/PlaylistTableModel.java
@@ -38,11 +38,11 @@ public class PlaylistTableModel extends AbstractTableModel {
/**
* 空ã®ãã©ãã¯ãªã¹ãã¢ãã«
*/
- SequenceTrackListTableModel emptyTrackListTableModel;
+ SequenceTrackListTableModel emptyTrackListTableModel = new SequenceTrackListTableModel(this, null, null);
/**
* 空ã®ã¤ãã³ããªã¹ãã¢ãã«
*/
- TrackEventListTableModel emptyEventListTableModel;
+ TrackEventListTableModel emptyEventListTableModel = new TrackEventListTableModel(emptyTrackListTableModel, null);
/**
* é¸æããã¦ããã·ã¼ã±ã³ã¹ã®ã¤ã³ããã¯ã¹
*/
@@ -59,9 +59,10 @@ public class PlaylistTableModel extends AbstractTableModel {
Object src = event.getSource();
if( src instanceof MidiSequencerModel ) {
int newValue = ((MidiSequencerModel)src).getValue() / 1000;
- if(value == newValue) return;
- value = newValue;
- fireTableCellUpdated(indexOfSequenceOnSequencer(), Column.POSITION.ordinal());
+ if(value != newValue) {
+ value = newValue;
+ fireTableCellUpdated(indexOfSequenceOnSequencer(), Column.POSITION.ordinal());
+ }
}
}
@Override
@@ -76,8 +77,8 @@ public class PlaylistTableModel extends AbstractTableModel {
public PlaylistTableModel(MidiSequencerModel sequencerModel) {
this.sequencerModel = sequencerModel;
sequencerModel.addChangeListener(mmssPosition);
- // EOF(0x2F)ãæ¥ããæ²ã®çµãããªã®ã§æ¬¡ã®æ²ã¸é²ãã
sequencerModel.getSequencer().addMetaEventListener(msg->{
+ // EOF(0x2F)ãæ¥ã¦æ²ãçµãã£ãã次ã®æ²ã¸é²ãã
if(msg.getType() == 0x2F) SwingUtilities.invokeLater(()->{
try {
goNext();
@@ -86,8 +87,6 @@ public class PlaylistTableModel extends AbstractTableModel {
}
});
});
- emptyTrackListTableModel = new SequenceTrackListTableModel(this, null, null);
- emptyEventListTableModel = new TrackEventListTableModel(emptyTrackListTableModel, null);
}
/**
* 次ã®æ²ã¸é²ã¿ã¾ãã
@@ -96,6 +95,7 @@ public class PlaylistTableModel extends AbstractTableModel {
* 次ã®æ²ããªããã°ãããã§åæ¢ãã¾ãããããã®å ´åãæ²ã®å
é ã¸æ»ãã¾ãã
*
* @throws InvalidMidiDataException {@link Sequencer#setSequence(Sequence)} ãåç
§
+ * @throws IllegalStateException MIDIã·ã¼ã±ã³ãµããã¤ã¹ãéãã¦ããå ´å
*/
private void goNext() throws InvalidMidiDataException {
// ã¨ããããæ²ã®å
é ã¸æ»ã
@@ -217,15 +217,15 @@ public class PlaylistTableModel extends AbstractTableModel {
public boolean isCellEditable() { return true; } // ããã«ã¯ãªãã¯ã ãæå¹
@Override
public Object getValueOf(SequenceTrackListTableModel sequenceModel) {
- return sequenceModel.isOnSequencer() ? sequenceModel.getParent().mmssPosition : "";
+ if( ! sequenceModel.isOnSequencer() ) return "";
+ return sequenceModel.getParent().mmssPosition;
}
},
/** ã·ã¼ã±ã³ã¹ã®æéé·ï¼åï¼ç§ï¼ */
LENGTH("Length", String.class, 80) {
@Override
public Object getValueOf(SequenceTrackListTableModel sequenceModel) {
- long usec = sequenceModel.getSequence().getMicrosecondLength();
- int sec = (int)( (usec < 0 ? usec += 0x100000000L : usec) / 1000L / 1000L );
+ int sec = (int)( sequenceModel.getMicrosecondLength() / 1000L / 1000L );
return String.format( "%02d:%02d", sec/60, sec%60 );
}
},
@@ -288,9 +288,7 @@ public class PlaylistTableModel extends AbstractTableModel {
return dtLabel == null ? "[Unknown]" : dtLabel;
}
};
- /**
- * ã¿ã¤ãã³ã°åå²å½¢å¼ã«å¯¾å¿ããã©ãã«æåå
- */
+ /** ã¿ã¤ãã³ã°åå²å½¢å¼ã«å¯¾å¿ããã©ãã«æåå */
private static final Map divisionTypeLabels = new HashMap() {
{
put(Sequence.PPQ, "PPQ");
@@ -366,11 +364,9 @@ public class PlaylistTableModel extends AbstractTableModel {
* ãã®ãã¬ã¤ãªã¹ãã«èªã¿è¾¼ã¾ããå
¨ã·ã¼ã±ã³ã¹ã®åè¨æéé·ãè¿ãã¾ãã
* @return å
¨ã·ã¼ã±ã³ã¹ã®åè¨æéé· [ç§]
*/
- public int getTotalTimeInSeconds() {
- return sequenceModelList.stream().mapToInt(m->{
- long usec = m.getSequence().getMicrosecondLength();
- return (int)( (usec < 0 ? usec += 0x100000000L : usec)/1000L/1000L );
- }).sum();
+ public int getSecondLength() {
+ // ãã¤ã¯ãç§åä½ã§ã®æ¡ããµããåé¿ãã¤ã¤ã丸ã誤差ãæå°éã«ãããããããªç§åä½ã§åè¨ãç®åºããã
+ return (int)(sequenceModelList.stream().mapToLong(m -> m.getMicrosecondLength() / 1000L).sum() / 1000L);
}
/**
* é¸æãããMIDIã·ã¼ã±ã³ã¹ã®ãã¼ãã«ã¢ãã«ãè¿ãã¾ãã
@@ -416,10 +412,10 @@ public class PlaylistTableModel extends AbstractTableModel {
if( sequence == null ) sequence = (new ChordProgression()).toMidiSequence();
sequenceModelList.add(new SequenceTrackListTableModel(this, sequence, filename));
//
- // æ«å°¾ã«è¡ã追å ãããã®ã§ãåæç»ãã¦ããã
+ // æ«å°¾ã«è¿½å ãããè¡ãé¸æããåæç»
int lastIndex = sequenceModelList.size() - 1;
- fireTableRowsInserted(lastIndex, lastIndex);
sequenceListSelectionModel.setSelectionInterval(lastIndex, lastIndex);
+ fireTableRowsInserted(lastIndex, lastIndex);
return lastIndex;
}
/**
@@ -427,6 +423,7 @@ public class PlaylistTableModel extends AbstractTableModel {
* @param sequence MIDIã·ã¼ã±ã³ã¹
* @return 追å ãããã·ã¼ã±ã³ã¹ã®ã¤ã³ããã¯ã¹ï¼å
é ã 0ï¼
* @throws InvalidMidiDataException {@link Sequencer#setSequence(Sequence)} ãåç
§
+ * @throws IllegalStateException MIDIã·ã¼ã±ã³ãµããã¤ã¹ãéãã¦ããå ´å
*/
public int play(Sequence sequence) throws InvalidMidiDataException {
int lastIndex = add(sequence,"");
@@ -442,13 +439,16 @@ public class PlaylistTableModel extends AbstractTableModel {
* é¤å»ãããã·ã¼ã±ã³ã¹ãã·ã¼ã±ã³ãµã¼ã«ãã¼ãæ¸ã¿ã®å ´åãã¢ã³ãã¼ããã¾ãã
*
* @throws InvalidMidiDataException {@link Sequencer#setSequence(Sequence)} ãåç
§
+ * @throws IllegalStateException MIDIã·ã¼ã±ã³ãµããã¤ã¹ãéãã¦ããå ´å
*/
public void removeSelectedSequence() throws InvalidMidiDataException {
if( sequenceListSelectionModel.isSelectionEmpty() ) return;
int selectedIndex = sequenceListSelectionModel.getMinSelectionIndex();
SequenceTrackListTableModel removedSequence = sequenceModelList.remove(selectedIndex);
- if( removedSequence.isOnSequencer() ) sequencerModel.setSequenceTrackListTableModel(null);
fireTableRowsDeleted(selectedIndex, selectedIndex);
+ if( removedSequence.isOnSequencer() ) {
+ sequencerModel.setSequenceTrackListTableModel(null);
+ }
}
/**
* ãã¼ãã«å
ã®æå®ããã¤ã³ããã¯ã¹ä½ç½®ã«ããã·ã¼ã±ã³ã¹ãã·ã¼ã±ã³ãµã¼ã«ãã¼ããã¾ãã
@@ -457,10 +457,11 @@ public class PlaylistTableModel extends AbstractTableModel {
*
* @param newRowIndex ãã¼ãããã·ã¼ã±ã³ã¹ã®ã¤ã³ããã¯ã¹ä½ç½®ãã¢ã³ãã¼ãããã¨ã㯠-1
* @throws InvalidMidiDataException {@link Sequencer#setSequence(Sequence)} ãåç
§
+ * @throws IllegalStateException MIDIã·ã¼ã±ã³ãµããã¤ã¹ãéãã¦ããã¨ãã«ã¢ã³ãã¼ããããã¨ããå ´å
*/
public void loadToSequencer(int newRowIndex) throws InvalidMidiDataException {
SequenceTrackListTableModel oldSeq = sequencerModel.getSequenceTrackListTableModel();
- SequenceTrackListTableModel newSeq = (newRowIndex < 0 ? null : sequenceModelList.get(newRowIndex));
+ SequenceTrackListTableModel newSeq = (newRowIndex < 0 || sequenceModelList.isEmpty() ? null : sequenceModelList.get(newRowIndex));
if( oldSeq == newSeq ) return;
sequencerModel.setSequenceTrackListTableModel(newSeq);
int columnIndices[] = {
diff --git a/src/camidion/chordhelper/midieditor/SequenceTrackListTableModel.java b/src/camidion/chordhelper/midieditor/SequenceTrackListTableModel.java
index f9f6fa1..78c74ac 100644
--- a/src/camidion/chordhelper/midieditor/SequenceTrackListTableModel.java
+++ b/src/camidion/chordhelper/midieditor/SequenceTrackListTableModel.java
@@ -13,6 +13,7 @@ import javax.swing.DefaultListSelectionModel;
import javax.swing.ListSelectionModel;
import javax.swing.table.AbstractTableModel;
+import camidion.chordhelper.mididevice.MidiSequencerModel;
import camidion.chordhelper.music.MIDISpec;
/**
@@ -215,6 +216,15 @@ public class SequenceTrackListTableModel extends AbstractTableModel {
*/
public Sequence getSequence() { return sequence; }
/**
+ * MIDIã·ã¼ã±ã³ã¹ã®ãã¤ã¯ãç§åä½ã®é·ããè¿ãã¾ãã
+ * æ²ãé·ãã㦠{@link Sequence#getMicrosecondLength()} ãè² æ°ãè¿ãã¦ãã¾ã£ãå ´åã®è£æ£ãè¡ãã¾ãã
+ * @return MIDIã·ã¼ã±ã³ã¹ã®é·ã[ãã¤ã¯ãç§]
+ */
+ public long getMicrosecondLength() {
+ long usec = sequence.getMicrosecondLength();
+ return usec < 0 ? usec += 0x100000000L : usec;
+ }
+ /**
* ã·ã¼ã±ã³ã¹tickã¤ã³ããã¯ã¹ãè¿ãã¾ãã
* @return ã·ã¼ã±ã³ã¹tickã¤ã³ããã¯ã¹
*/
@@ -226,7 +236,8 @@ public class SequenceTrackListTableModel extends AbstractTableModel {
private void setSequence(Sequence sequence) {
//
// æ§ã·ã¼ã±ã³ã¹ã®é²é³ã¢ã¼ãã解é¤
- sequenceListTableModel.getSequencerModel().getSequencer().recordDisable(null); // The "null" means all tracks
+ MidiSequencerModel sequencerModel = sequenceListTableModel.getSequencerModel();
+ if( sequencerModel != null ) sequencerModel.getSequencer().recordDisable(null);
//
// ãã©ãã¯ãªã¹ããã¯ãªã¢
int oldSize = trackModelList.size();