File APIs for Java Developers
Manipulate DOC, XLS, PPT, PDF and many others from your application.
http://aspose.com/file-tools
The moose likes Beginning Java and the fly likes Application doesn't quit -- MiniMiniMusicApp sample from Head First Java Big Moose Saloon
  Search | Java FAQ | Recent Topics | Flagged Topics | Hot Topics | Zero Replies
Register / Login
JavaRanch » Java Forums » Java » Beginning Java
Bookmark "Application doesn Watch "Application doesn New topic
Author

Application doesn't quit -- MiniMiniMusicApp sample from Head First Java

Peter Karp
Greenhorn

Joined: May 18, 2006
Posts: 6
Hi,

I don't find the reason why MiniMiniMusicApp hangs. I tried to add a player.close() after looking in the API docs, but that doesn't help :-/ Any ideas what goes wrong?

Here's the source:




import javax.sound.midi.*;
import javax.sound.midi.Sequence;


public class MiniMiniMusicApp {

public static void main(String[] args) {
MiniMiniMusicApp mini = new MiniMiniMusicApp();
mini.play();
}

public void play() {
try {
Sequencer player = MidiSystem.getSequencer();
player.open();

Sequence seq = new Sequence(Sequence.PPQ, 4);

Track track = seq.createTrack();

ShortMessage a = new ShortMessage();
a.setMessage(ShortMessage.NOTE_ON, 1, 44, 100);
MidiEvent noteOn = new MidiEvent(a, 1);
track.add(noteOn);

ShortMessage b = new ShortMessage();
a.setMessage(ShortMessage.NOTE_OFF, 1, 44, 100);
MidiEvent noteOff = new MidiEvent(b, 16);
track.add(noteOff);

player.setSequence(seq);
player.start();
player.close();

}
catch (Exception ex) {
ex.printStackTrace();
}
}
}
Daniel Lucas
Ranch Hand

Joined: Apr 24, 2006
Posts: 48
What page is this application found in Head First Java ? I have the book, so I'd like to try typing the code in myself and compiling.
Campbell Ritchie
Sheriff

Joined: Oct 13, 2005
Posts: 38107
    
  22
Have you any idea where it hangs?
It hasn't got multiple threads, has it?
Have you tried it on a full-blown IDE? That means NetBeans or Eclipse or similar. Put it on an IDE, set a breakpoint somewhere, and then follow its execution with the debugger. See how far it gets and where it hangs.

See whether that gives you some idea what is going wrong, then come back.

I am not familiar with these musical programs myself; maybe somebody else can help better.
Michael Dunn
Ranch Hand

Joined: Jun 09, 2003
Posts: 4632
don't know if this is the best way, but it seems to work OK on this app.

Peter Karp
Greenhorn

Joined: May 18, 2006
Posts: 6
Thanks for all the answers. The example is from page 342 in Head First Java (2nd edition).

_I_ haven't created a new thread, but I'm not sure if this might be the answer to the question. I have used a text editor and Netbeans. There is no difference. The program itself runs, but it will not stop, so setting a breakpoint won't help. I found a typo in my first posting (a instead of b), but that doesn't effect the problem.

I finally found the source code for the book and in the file there are some important differences to the printed version. I have added a /////new comment in the added lines.


// --------- code begin --------------

import javax.sound.midi.*;


public class MiniMiniMusicApp { // this is the first one

public static void main(String[] args) {
MiniMiniMusicApp mini = new MiniMiniMusicApp();
mini.play();
}

public void play() {

try {

// make (and open) a sequencer, make a sequence and track

Sequencer sequencer = MidiSystem.getSequencer();
sequencer.open();

Sequence seq = new Sequence(Sequence.PPQ, 4);
Track track = seq.createTrack();

// now make two midi events (containing a midi message)
MidiEvent event = null; //////////new

// first make the message
// then stick the message into a midi event
// and add the event to the track

ShortMessage a = new ShortMessage();
a.setMessage(144, 1, 44, 100);
MidiEvent noteOn = new MidiEvent(a, 1); // <-- means at tick one, the above event happens
track.add(noteOn);

ShortMessage b = new ShortMessage();
b.setMessage(128, 1, 44, 100);
MidiEvent noteOff = new MidiEvent(b, 16); // <-- means at tick one, the above event happens
track.add(noteOff);

// add the events to the track

// add the sequence to the sequencer, set timing, and start
sequencer.setSequence(seq);

sequencer.start();
Thread.sleep(1000); /////////new
sequencer.close(); /////////new
System.exit(0); ////////new
} catch (Exception ex) {ex.printStackTrace();}
} // close play

} // close class


// --------- code end --------------

The first difference is
MideEvent event = null;
which is _not_used anywhere in the program!?

Then later
Thread.sleep(1000); /////////new
sequencer.close(); /////////new
System.exit(0); ////////new
are added.

Threads are not explained at this point in the book, but without the sleep()-method the piano tone can not always be heard when one closes the sequencer. If the sequencer is not closed the program will not terminate, neither on Windows XP nor on OS X.

After forcing the thread to sleep so the tone can be heard the sequencer is closed. I found this myself by looking in the API docs. And now comes an interesting point I found out.

sequencer.close() is sufficient for the program to stop itself when I run the program in Windows XP. But when running the program on OS X (with latest Java 5) the program will not terminate. One has to add
System.exit();

I'm somewhat confused now about the different behavior and the additional System.exit() needed on OS X.

It took me quite some time to figure these things out. That's not the real problem, but IMO this wasn't neccessary. There's an errata for the book which fixes errors, but this wrong listing is not mentioned, allthough I found two postings on the Javaranch forum which asked a similar question to mine. One was not answered at all. The other was

http://www.coderanch.com/t/399099/java/java/stop-music

I twice e-mailed Kathy and Bert (the authors) with suggestions and questions, but got no answer :-( I hoped that a here -- the official unofficial "Head First Java" homepage -- would be a place where additions to the book could be posted or better could be organized in a Wiki. This would be greatly beneficial for the readers of the book.

If someone knows how to get through to Kathy and Bert I like to get a pointer (not a reference here ;-)

Thank you for taking the time to read and answer my post.

Greetings from germany
Peter
Bobby Roberts
Greenhorn

Joined: Sep 26, 2006
Posts: 3
Thanks for you guys' input. I couldn't even get the darn code to compile the way it was written in the book and even from their printed out code from wickedlysmart.com.

I kept getting the following errors.

MiniMiniMusicApp.java:20: cannot find symbol
symbol : variable PPQ
location: class Sequence
Sequence seq = new Sequence(Sequence.PPQ, 4);
^
MiniMiniMusicApp.java:20: internal error; cannot instantiate Sequence.<init> at
Sequence to ()
Sequence seq = new Sequence(Sequence.PPQ, 4);
^
MiniMiniMusicApp.java:22: cannot find symbol
symbol : method createTrack()
location: class Sequence
Track track = seq.createTrack();
^
MiniMiniMusicApp.java:34: cannot find symbol
symbol : method setSequence(Sequence)
location: interface javax.sound.midi.Sequencer
player.setSequence(seq);


I see that some of you guys also imported the javax.sound.midi.Sequence class explicitly and that made it compile and run (it never terminated, but the solution to that problem works as well).

But my question is why would have to import the javax.sound.midi.Sequence class explicitly if I already imported javax.sound.midi.*? Doesn't the * automatically include everything in that package?

In other words, isnt the code below redundant? And if so why do I have to do this to get the code to compile?

import javax.sound.midi.*;
import javax.sound.midi.Sequence;

[ September 26, 2006: Message edited by: Bobby Roberts ]
Jeffrey Martin
Greenhorn

Joined: Jan 29, 2007
Posts: 1

I am having the same issue. Both the MiniMiniMusicApp and the MiniMusicCmdLine applications run, play a note, and then just sit there. The program never terminates, and when I put some extra lines of System.out to find the hold-up, it just showed that the program does indeed complete main(). At that point there's nothing left to process, so what could keep it open?


-=-=-=-
Unicycle
Eric Daly
Ranch Hand

Joined: Jul 11, 2006
Posts: 143
@bobby, the code isn't redundant... code you use will leave off where you imported (example: Sequencer comes after javax.sound.midi.(Sequencer), so if you say javax.sound.midi.*, anywhere in your code you can say Sequencer, and really all the compiler does is add javax.sound.midi. right before it. so you say Sequencer player = MidiSystem.getSequencer(); and since you imported javax.sound.midi.*, the compiler automatically (invisibly) changes that to say javax.sound.midi.Sequencer player = javax.sound.midi.MidiSystem.getSequencer()
hope that made sense
So when you have to import javax.sound.midi.Sequence, it looks to me like somewhere you just said PPQ instead of Sequence.PPQ, and since PPQ extends javax.sound.midi.Sequence, the problem goes away when you import that.
As far as the program not terminating, I'm using Eclipse IDE, and had the same problem. I think I fixed it though... right after player.start(), I put Thread.sleep(1000) and then I put player.close(). I think because the player was never closed, the program never terminates. and Thread.sleep(1000) just makes sure 1000 milliseconds pass before the player closes. You can put in whatever you want, just make sure it's enough time to hear the music play before the program closes your player. Thread.sleep(1) will close it so fast you will hear nothing. Hope that helps!


Studying for SCJP 6
 
 
subject: Application doesn't quit -- MiniMiniMusicApp sample from Head First Java
 
Similar Threads
Head First Java Chapter 11 MiniMiniMusicApp
Java sounds not working!
Why doesn't my progam quit?
MiniMiniMusicApp? anyone else having issues with it?
Head First Java chapter 11 MiniMiniMusicApp