tags:

views:

530

answers:

9

Hi, I'm having some trouble playing MIDI files in Java. What I get is a MidiUnavailableException (MIDI OUT transmitter not available) when I try to play it. My code is standard:

try {
    midiseq = MidiSystem.getSequencer();
    midiseq.open();
    midiseq.setSequence(MidiSystem.getSequence(sound1));
    midiseq.setLoopCount(Sequencer.LOOP_CONTINUOUSLY);
    midiseq.start();
} catch (Exception e) {e.printStackTrace();}

midiseq is a Sequencer; sound1 is an InputStream.

This code works on several other computers, and even works in Eclipse and when used in a JAR file, just not when I launch it from the command prompt. I've downloaded a more stable Java midi application, and it threw the same exception.

It can't be a hardware problem because Eclipse can run it without problems, neither can it be a coding problem because this runs correctly on other computers. Even this one line of code throws this exception:

javax.sound.midi.MidiSystem.getSequencer();

Thanks in advance.

edit: My operating system is Windows Vista. Before I asked this question I've downloaded the latest JRE and JDK (1.6.0_13 I think).

edit: The code:

ClassLoader.getSystemClassLoader().loadClass("com.sun.media.sound.RealTimeSequencer");
System.out.println( "Sequencer class loaded" );// Otherwise ClassNotFoundException

prints "Sequencer class loaded."

But this code:

  try{
        System.out.println(javax.sound.midi.MidiSystem.getSequencer());
        System.exit(0);
      } catch(Exception e) {
        throw new RuntimeException(e);
      }
      System.exit(1);

throws the MidiUnavailableException.

Also, this code:

 MidiDevice.Info[] devices = MidiSystem.getMidiDeviceInfo();
 if (devices.length == 0) {
     System.out.println("No MIDI devices found");
 } else {
     for (MidiDevice.Info dev : devices) {
         System.out.println(dev);
     }
 }

gives me this:

    Microsoft MIDI Mapper
    Microsoft GS Wavetable Synth
    Real Time Sequencer
    Java Sound Synthesizer
+2  A: 

Is it possible that it has something to do with permissions? If you're running the JAR file as a different (more privileged) user than the plain command-line program, that might explain the difference. If it's not that, maybe some Java system property... I can't think of anything else that would make a difference between running the same code as a JAR file or as individual .class files.

It might help if you edit the question to provide more details about the different ways you've been running the program.

David Zaslavsky
+1  A: 

Could you add your operating system and java version?

And post the exception; Java generally does a fair job saying whats wrong. It's just not always easy to understand :)

On my mac with java 1.5.0_16 I don't get an exception (on the command line).

The following program

public class MidiTester {

    public static void main(String[] args) {
      try{
        System.out.println(javax.sound.midi.MidiSystem.getSequencer());
        System.exit(0);
      } catch(Exception e) {
        throw new RuntimeException(e);
      }
      System.exit(1);
    }
}

prints

com.sun.media.sound.RealTimeSequencer@d08633

You could check whether you have the sequencer class on the classpath:

ClassLoader.getSystemClassLoader().loadClass("com.sun.media.sound.RealTimeSequencer");
System.out.println( "Sequencer class loaded" );// Otherwise ClassNotFoundException

This would at least make it clear whether you do not have the classes (in the java accessed via the PATH), or whether it's something different like a permission problem.

extraneon
+2  A: 

First have a look at the capabilities of your system:

MidiDevice.Info[] devices = MidiSystem.getMidiDeviceInfo();
if (devices.length == 0) {
    System.out.println("No MIDI devices found");
} else {
    for (MidiDevice.Info dev : devices) {
        System.out.println(dev);
    }
}

If there is nothing there, you might need to install soundbanks to enable the jvm to create a software sequencer.

Also check the output of MidiSystem.getReceiver() as the dreaded MidiUnavailableException will also occur if a receiver can not be created (MidiSystem javadoc).

I expect that installing the soundbank file will give the jvm the opportunity to fall back on a synthesizer receiver, and not require hardware access anymore (which seems to fail:)

extraneon
+1  A: 

WHen launching from the command prompt makes it fail, but launching from a JAR works, I'd check if you really use the same Java version for both cases. For the Jar, check file associations in Windows Explorer, and for the commandline, check whether java -version outputs the expected version (if not, dig through your PATH variable).

mihi
+1  A: 

Also (another shot in the dark), can you try and do a hard-shutdown on any other application that may be using sound and specifically Midi devices? I know that people get this problem on some Linuxes when another application uses Midi and doesn't release it.

Uri
+1  A: 

Point explorer to your JRE folder (the one above the bin folder on the $PATH you are using to run the program) e.g. "C:\Program Files\Java\jre1.6.0"

Go into the \lib folder. Do you see a folder called "audio"? Does it have anything in? If not, go to http://java.sun.com/products/java-media/sound/soundbanks.html

download any of the MIDI banks as described, and copy it into the said folder. let us know if it works!

Sanjay Manohar
I have seen this type of behaviour a few times due to not having a MIDI sound bank installed.
Sanjay Manohar
+1  A: 

Hi, I've found the same problem: unable to play MIDI. But I've noticed that the problem had started when I upgrade the JDK from 1.6.0_10 to 1.6.0_13.

I tested both JDKs with the simple program:

public class MidiTester {

public static void main(String[] args) {
  try{
    System.out.println(javax.sound.midi.MidiSystem.getSequencer());
    System.exit(0);
  } catch(Exception e) {
    throw new RuntimeException(e);
  }
  System.exit(1);
}

}

JDK 1.6.0_10 gave the result: com.sun.media.sound.RealTimeSequencer@1bd747

JDK 1.6.0_13 gave the result: Exception in thread "main" java.lang.RuntimeException: javax.sound.midi.MidiUnavailableException: MIDI OUT transmitter not available at ivan.seaquest.MidiTester.main(MidiTester.java:10) Caused by: javax.sound.midi.MidiUnavailableException: MIDI OUT transmitter not available at com.sun.media.sound.AbstractMidiDevice.createTransmitter(AbstractMidiDevice.java:444) at com.sun.media.sound.AbstractMidiDevice.getTransmitter(AbstractMidiDevice.java:299) at javax.sound.midi.MidiSystem.getSequencer(MidiSystem.java:451) at javax.sound.midi.MidiSystem.getSequencer(MidiSystem.java:348) at ivan.seaquest.MidiTester.main(MidiTester.java:7)

I'm going to create a bug at Sun. I hope it helps...

A: 

I have had the same problem. The error was caused by JMF included in the classpath.

Axel