2010-10-21 32 views
1

J'utilise la méthode suivante pour lire un son enregistré, cela fonctionne bien, mais pourquoi il ne joue qu'une fois, la deuxième fois que je clique sur le bouton de lecture, il ne fait rien, comment réinitialiser les données?Le son de Java n'est lu qu'une fois?

// Write data to the OutputChannel. 
    public class Playback implements Runnable 
    { 
    SourceDataLine line; 
    Thread thread; 

    public void start() 
    { 
     errStr=null; 
     thread=new Thread(this); 
     thread.setName("Playback"); 
     thread.start(); 
    } 

    public void stop() { thread=null; } 

    private void shutDown(String message) 
    { 
     if ((errStr=message)!=null) 
     { 
     System.err.println(errStr); 
     samplingGraph.repaint(); 
     } 
     if (thread!=null) 
     { 
     thread=null; 
     samplingGraph.stop(); 
     if (Java_Sound.Running_In_All_Permissions_Mode) captB.setEnabled(true); 
     pausB.setEnabled(false); 
     playB.setText("Play"); 
     } 
    } 

    public void run() 
    { 
     AudioFormat format=formatControls.getFormat();            // get an AudioInputStream of the desired format for playback 
     AudioInputStream playbackInputStream=AudioSystem.getAudioInputStream(format,audioInputStream); 

     if (playbackInputStream==null) 
     { 
     shutDown("Unable to convert stream of format "+audioInputStream+" to format "+format); 
     return; 
     } 
     SourceDataLine.Info info=new DataLine.Info(SourceDataLine.class,format);      // define the required attributes for our line,and make sure a compatible line is supported. 

     if (AudioSystem.isLineSupported(info)) 
     { 
     try                      // get and open the source data line for playback. 
     { 
      line=(SourceDataLine)AudioSystem.getLine(info); 
      line.open(format,bufSize); 
     } 
     catch (LineUnavailableException ex) 
     { 
      shutDown("Unable to open the line: "+ex); 
      return; 
     } 
     int frameSizeInBytes=format.getFrameSize();            // play back the captured audio data 
     int bufferLengthInFrames=line.getBufferSize()/8; 
     int bufferLengthInBytes=bufferLengthInFrames*frameSizeInBytes; 
     byte[] data=new byte[bufferLengthInBytes]; 
     int numBytesRead=0; 
     line.start();                    // start the source data line 
     while (thread!=null) 
     { 
      try 
      { 
      if ((numBytesRead=playbackInputStream.read(data))==-1) break; 
      int numBytesRemaining=numBytesRead; 
      while (numBytesRemaining>0) { numBytesRemaining-=line.write(data,0,numBytesRemaining); } 
      } 
      catch (Exception e) 
      { 
      shutDown("Error during playback: "+e); 
      break; 
      } 
     } 
     } 
     if (thread!=null) line.drain();                // we reached the end of the stream. Let the data play out,then stop and close the line. 
     line.stop(); 
     line.close(); 
     line=null; 
     shutDown(null); 
    } 
    } 

Après mon test, je trouve cette ligne est à l'origine du problème

« if ((numBytesRead=playbackInputStream.read(data))==-1) break; »

La première fois que je jouais en arrière, il y avait des données, il a bien fonctionné, mais la deuxième fois, ça s'est cassé. Pourquoi ? Comment le réparer ?

Répondre

0

I figured it out, ajoutez la ligne suivante après "shutdown (null)"

if (file==null) 
    try { audioInputStream.reset(); } 
    catch (Exception e) { e.printStackTrace(); } 

Maintenant, il fonctionne parfaitement.

0

Jamais travaillé avec Java audio, mais puisque vous utilisez le flux, vous devez soit réinitialiser le flux si cette option est disponible, ou besoin de créer un nouveau flux chaque fois que vous le lisez.