Click to See Complete Forum and Search --> : Applet hangs while using JOptionPane.xxx()


Basit56
August 8th, 2009, 02:31 AM
Hi to all,
Hope you all will be fine. I have an applet of voicerecorder. The problem is when you start to record the sound it works fine.Now i want to put a condition in it, that sound can not be recorded more than 3 minutes for this, in the initial step i put the condition like

if(minutes > 3){
JOptionPane.showMessageDialog(null, "Yor are not allowed to record more than 3 minutes", "Warning",JOptionPane.WARNING_MESSAGE);
}
But after executing this it shows a dialog box with nothing in it and after showing a long arror messages in the NetBeans output pane and when i click the exit button then the applet exits.The code snippet is as follws that do this part

public void start() {
thread = new Thread(this);
thread.setName("SamplingGraph");
thread.start();
seconds = 0;
minutes = 0;
}

public void stop() {
if (thread != null) {
thread.interrupt();
}
thread = null;
}

public void run() {
seconds = 0;
minutes = 0;
while (thread != null) {
if ((playback.line != null) && (playback.line.isOpen()) ) {

int milliseconds = (int)(capture.line.getMicrosecondPosition() / 1000);
seconds =(int) (milliseconds / 1000.0);
minutes = (int)((milliseconds / 1000.0) / 60 );


} else if ( (capture.line != null) && (capture.line.isActive()) ) {

int milliseconds = (int)(capture.line.getMicrosecondPosition() / 1000);
seconds =(int) (milliseconds / 1000.0);
minutes = (int)((milliseconds / 1000.0) / 60 );
}

try { thread.sleep(100); } catch (Exception e) { break; }

repaint();

while ((capture.line != null && !capture.line.isActive()) ||
(playback.line != null && !playback.line.isOpen()))
{
try { thread.sleep(10); } catch (Exception e) { break; }
}
}
seconds = 0;
minutes = 0;
repaint();
}

Then the part where i modify the things and things start going wrong
public void paint(Graphics g) {

Dimension d = getSize();
int w = d.width;
int h = d.height;
int INFOPAD = 15;

Graphics2D g2 = (Graphics2D) g;
g2.setBackground(getBackground());
g2.clearRect(0, 0, w, h);
g2.setColor(Color.white);
g2.fillRect(0, h-INFOPAD, w, INFOPAD);

if (errStr != null) {
g2.setColor(jfcBlue);
g2.setFont(new Font("serif", Font.BOLD, 18));
g2.drawString("ERROR", 5, 20);
AttributedString as = new AttributedString(errStr);
as.addAttribute(TextAttribute.FONT, font12, 0, errStr.length());
AttributedCharacterIterator aci = as.getIterator();
FontRenderContext frc = g2.getFontRenderContext();
LineBreakMeasurer lbm = new LineBreakMeasurer(aci, frc);
float x = 5, y = 25;
lbm.setPosition(0);
while (lbm.getPosition() < errStr.length()) {
TextLayout tl = lbm.nextLayout(w-x-5);
if (!tl.isLeftToRight()) {
x = w - tl.getAdvance();
}
tl.draw(g2, x, y += tl.getAscent());
y += tl.getDescent() + tl.getLeading();
}
} else if (capture.thread != null) {
g2.setColor(Color.black);
g2.setFont(font12);
g2.drawString("Length: " + String.valueOf( minutes) + " min" + " : " + String.valueOf(seconds) + " sec", 3, h-4);
if(minutes > 3){
JOptionPane.showMessageDialog(null, "Yor are not allowed to record more than three minutes", "Warning",JOptionPane.WARNING_MESSAGE);
capture.stop();
fileName = " Press Done when complete";
samplingGraph.stop();
playButton.setEnabled(true);
pauseButton.setEnabled(false);
doneButton.setEnabled(true);
recordButton.setText("Record");
}


} else {
g2.setColor(Color.black);
g2.setFont(font12);
g2.drawString( fileName , 3, h-4);
// g2.drawString("File has been recorded." , 3, h-4);

if (audioInputStream != null) {
// .. render sampling graph ..
g2.setColor(jfcBlue);
for (int i = 1; i < lines.size(); i++) {
g2.draw((Line2D) lines.get(i));
}

// .. draw current position ..
if (seconds != 0) {
double loc = seconds/duration*w;
g2.setColor(pink);
g2.setStroke(new BasicStroke(3));
g2.draw(new Line2D.Double(loc, 0, loc, h-INFOPAD-2));
}
}
}

Please tell me where i m wrong.I attach file but its size exceeds the size limit so i m unable to attach it
Thanks in advance

dlorde
August 8th, 2009, 04:19 AM
If you're going to post code, post it inside [CODE]...[/CODE] tags so it is readable, and if possible include complete methods (if not classes), not code snippets. If you get error messages post the full error message here (including stack trace if present). Error messages generally tell you what the problem is.

Don't worry about people stealing your ideas. If your ideas are any good, you'll have to ram them down people's throats...
H. Aiken

Basit56
August 8th, 2009, 05:38 AM
Hi,
OOOpps.Sorry next time i will be carefull. Thanks :)

keang
August 8th, 2009, 06:03 AM
OOOpps.Sorry next time i will be carefull. ThanksNo problem, but how about starting now rather than next time and then we can try to answer your question.

Please do as dlorde has asked and edit your original post to include code tags and add a new post which has the full error message and the code the error message relates to.

Basit56
August 8th, 2009, 06:12 AM
Hi,
Thanks.I modify my post using [CODE] tag. Thanks for your help :)

keang
August 8th, 2009, 08:47 AM
And where's the full error message :rolleyes:

dlorde
August 8th, 2009, 06:34 PM
Hi,
Thanks.I modify my post using [CODE] tag. Thanks for your help :)Er, the point of using the [CODE]...[/CODE] tags is to maintain the code formatting (indentation, etc) so that it is readable. You code is still unformatted and unreadable - did you write it like that?

Programs must be written for people to read, and only incidentally for machines to execute...
H. Abelson and G. Sussman

Basit56
August 10th, 2009, 01:41 AM
Hi,
This is the formatted code.Hope this time is readable :)


public void start() {
thread = new Thread(this);
thread.setName("SamplingGraph");
thread.start();
seconds = 0;
minutes = 0;
}

public void stop() {
if (thread != null) {
thread.interrupt();
}

thread = null;
}


public void run() {
seconds = 0;
minutes = 0;
while (thread != null) {
if ((playback.line != null) && (playback.line.isOpen()) ) {
int milliseconds = (int)(capture.line.getMicrosecondPosition() / 1000);
seconds =(int)((milliseconds / 1000.0) % 60 ) ;
minutes = (int)((milliseconds / 1000.0) / 60 );
} else if ( (capture.line != null) && (capture.line.isActive()) ) {

long milliseconds = (long)(capture.line.getMicrosecondPosition() / 1000);
seconds =(int) (milliseconds / 1000.0);
minutes = (int)((milliseconds / 1000.0) / 60 );
}

try { thread.sleep(100); } catch (Exception e) { break; }

repaint();

while ((capture.line != null && !capture.line.isActive()) ||
(playback.line != null && !playback.line.isOpen()))
{
try { thread.sleep(10); } catch (Exception e) { break; }
}
}

seconds = 0;
minutes = 0; //by basit
repaint();
}
} // End class SamplingGraph



And the code where i change the things and thing goes wrong


public void paint(Graphics g) {
Dimension d = getSize();
int w = d.width;
int h = d.height;
int INFOPAD = 15;

Graphics2D g2 = (Graphics2D) g;
g2.setBackground(getBackground());
g2.clearRect(0, 0, w, h);
g2.setColor(Color.white);
g2.fillRect(0, h-INFOPAD, w, INFOPAD);

if (errStr != null) {
g2.setColor(jfcBlue);
g2.setFont(new Font("serif", Font.BOLD, 18));
g2.drawString("ERROR", 5, 20);
AttributedString as = new AttributedString(errStr);
as.addAttribute(TextAttribute.FONT, font12, 0, errStr.length());
AttributedCharacterIterator aci = as.getIterator();
FontRenderContext frc = g2.getFontRenderContext();
LineBreakMeasurer lbm = new LineBreakMeasurer(aci, frc);
float x = 5, y = 25;
lbm.setPosition(0);
while (lbm.getPosition() < errStr.length()) {
TextLayout tl = lbm.nextLayout(w-x-5);
if (!tl.isLeftToRight()) {
x = w - tl.getAdvance();
}
tl.draw(g2, x, y += tl.getAscent());
y += tl.getDescent() + tl.getLeading();
}
} else if (capture.thread != null) {
g2.setColor(Color.black);
g2.setFont(font12);
g2.drawString("Length: " + String.valueOf( minutes) + " min" + " : " + String.valueOf(seconds % 60) + " sec", 3, h-4);

if(seconds > 180){
JOptionPane.showMessageDialog(null, "Yor are not allowed to record more than 3 minutes", "Warning", JOptionPane.WARNING_MESSAGE);

lines.removeAllElements();
capture.stop();
fileName = " Yor are not allowed to record more than three minutes.Press Done.";
samplingGraph.stop();
playButton.setEnabled(true);
pauseButton.setEnabled(false);
doneButton.setEnabled(true);
recordButton.setText("Record");
}
} else {
g2.setColor(Color.black);
g2.setFont(font12);
g2.drawString( fileName , 3, h-4);

if (audioInputStream != null) {
// .. render sampling graph ..
g2.setColor(jfcBlue);
for (int i = 1; i < lines.size(); i++) {
g2.draw((Line2D) lines.get(i));
}

// .. draw current position ..
if (seconds != 0) {
double loc = seconds/duration*w;
g2.setColor(pink);
g2.setStroke(new BasicStroke(3));
g2.draw(new Line2D.Double(loc, 0, loc, h-INFOPAD-2));
}
}
}
}


I hope this time you will surely read the code. I also attach a file with a snapshot of the screen after running the code.One thing that when i use System.out.println() instead of JOptionPane it works fine.

dlorde
August 10th, 2009, 07:56 AM
Without the error message text we asked for, I can't be specific, and I don't have time to try to recreate the problem, but I'm guessing that you get this problem because you've put a whole bunch of stuff in the paint(..) method that shouldn't be there - especially the call to JOptionPane.

The paint(..) method is a callback that the system calls whenever it needs to paint the component. You can assume this is likely to happen whenever what's being displayed changes (new windows or dialogs, frames or components moved, etc). As a result, as little as possible should be done in paint methods, and they should be made as quick and efficient as possible. Also, you should probably be overriding the paintComponent(..) method, rather than the paint(..) method. See Painting In AWT & Swing (http://java.sun.com/products/jfc/tsc/articles/painting/index.html).

I'm guessing that when your paint method displays the JOptionPane, the system will notice that your component needs repainting because the display has changed, so it will call your paint method again, which will try to display another JOptionPane... etc, recursing until it runs out of stack space. Or maybe the JOptionPane will just block the paint method and the event thread that called it, locking the application... I suspect the former.

You need to redesign the application workflow. Strip as much as possible out of that paint method - if possible, leave only the paint/draw commands. Do as much of the maths as possible in advance, and hold the values in class fields ready to be drawn. Never put any user interface code in a paint method.

Great software, likewise, requires a fanatical devotion to beauty. If you look inside good software, you find that parts that no one is ever supposed to see are beautiful too. When it comes to code I behave in a way that would make me eligible for prescription drugs if I approached everyday life the same way. It drives me crazy to see code that's badly indented, or that uses ugly variable names...
P. Graham

Basit56
August 12th, 2009, 05:29 AM
Hi,
Thanks you for your help :)