播放的音频超过了java中的设置持续时间

时间:2015-03-19 20:04:57

标签: java audio javasound

我将来自用户的短信作为输入。根据短信中的字母,我正在维护一个数组(在代码中命名为持续时间),它存储了必须播放audio1的时间。

我或者在特定位置的循环中播放两个音频文件并停止它们。

播放第一个音频文件直到第一个字母的持续时间,然后第二个音频文件设置为具有持续时间值的位置值并播放到持续时间+ 2秒。每次适当增加值。

但是当我播放它时,有时会停在正确的位置(比如前两次迭代),但有时会超出设定位置并开始完全播放音频文件直到结束。

为什么会这样?

我正在使用eclipse来编写和运行java代码。

我的java代码。

import java.util.Scanner;
import java.io.File;
import java.io.IOException;
import javax.sound.*; 
import javax.sound.sampled.AudioFormat;
import javax.sound.sampled.AudioInputStream;
import javax.sound.sampled.AudioSystem;
import javax.sound.sampled.Clip;
import javax.sound.sampled.DataLine;
import javax.sound.sampled.LineEvent;
import javax.sound.sampled.LineListener;
import javax.sound.sampled.LineUnavailableException;
import javax.sound.sampled.UnsupportedAudioFileException;

public class Stegano implements LineListener{

    /**
     * @param args
     */
    static long[] duration;
    static boolean playCompleted1;
    static boolean playCompleted2;
    static int ch;
    static float rate,r;

    //public static AudioFormat.Encoding PCM_SIGNED;
    public static AudioFormat getOutFormat(AudioFormat inFormat){
        ch = inFormat.getChannels();
        rate = inFormat.getSampleRate();
        r = rate;
    //  convertToFrames();
        return new AudioFormat(AudioFormat.Encoding.PCM_SIGNED ,7200,16,ch,ch*2,rate,inFormat.isBigEndian());
    }
    /*public static void convertToFrames(){
        int i ;
        for(i=0;i<duration.length;i++){
            duration[i] = (r*duration[i])/1000;
            System.out.println(duration[i]);
        }
    }*/
    void convertToAudio(){
        final File file1 = new File("E:/Jeena_Jeena_wapking.wav");
        final File file2 = new File("E:/Jeena_Jeena_wapking.wav");

        try {
            AudioInputStream in1 = AudioSystem.getAudioInputStream(file1);
            AudioInputStream in2 = AudioSystem.getAudioInputStream(file2);

            AudioFormat inForm1 = getOutFormat(in1.getFormat());
            AudioFormat inForm2 = getOutFormat(in2.getFormat());

            DataLine.Info info1 = new DataLine.Info(Clip.class,inForm1);
            DataLine.Info info2 = new DataLine.Info(Clip.class,inForm2);

            Clip clip1 = (Clip)AudioSystem.getLine(info1);
            Clip clip2 = (Clip)AudioSystem.getLine(info2);

            long d = 0;
            int i;
            long dt = clip1.getMicrosecondLength();
            System.out.println("Duration : " + (float)((dt / 1000000)/60.0) + "min");
            for(i=0;i< duration.length;i++){

                    System.out.println("i" + i);
                    in1 = AudioSystem.getAudioInputStream(file1);
                    inForm1 = getOutFormat(in1.getFormat());
                    info1 = new DataLine.Info(Clip.class,inForm1);
                    clip1 = (Clip)AudioSystem.getLine(info1);
                    clip1.addLineListener(this);
                    clip1.open(in1);
                    clip1.setMicrosecondPosition(d);

                    long pos = 0; 
                    clip1.start();


                    while(true){
                        pos = clip1.getMicrosecondPosition();
                        System.out.println("pos 1: " + pos);
                        if( pos == (d + duration[i])){
                            System.out.println("posFinal : " + pos);

                            clip1.stop();
                            break;
                        }   
                    }
                    while (!playCompleted1) {
                        // wait for the playback completes
                        try {
                            Thread.sleep(1000);
                        } catch (InterruptedException ex) {
                            ex.printStackTrace();
                        }
                    }
                    clip1.close();
                    playCompleted1 = false;
                    System.out.println("PLayback1 completed");
                    try {
                        Thread.sleep(8000);
                    } catch (InterruptedException ex) {
                        ex.printStackTrace();
                    }
                    d = d+pos;

                    in2 = AudioSystem.getAudioInputStream(file2);
                    inForm2 = in2.getFormat();
                    info2 = new DataLine.Info(Clip.class,inForm2);
                    clip2 = (Clip)AudioSystem.getLine(info2);
                    clip2.addLineListener(this);
                    clip2.open(in2);
                    clip2.setMicrosecondPosition(d);

                    d = d+2000000;
                    //pos = 0;
                    clip2.start();

                    while(true){
                        pos = clip2.getMicrosecondPosition();
                        System.out.println("pos 2: " + pos);
                        if( pos == d){
                            System.out.println("posFinal : " + pos);

                            clip2.stop();
                            break;
                        }   
                    }
                    while (!playCompleted1) {
                        // wait for the playback completes
                        try {
                            Thread.sleep(1000);
                        } catch (InterruptedException ex) {
                            ex.printStackTrace();
                        }
                    }
                    clip2.close();
                    System.out.println("PLayback2 completed");
                    try {
                        Thread.sleep(8000);
                    } catch (InterruptedException ex) {
                        ex.printStackTrace();
                    }
                    //d = pos + 2000000;
                    playCompleted1 = false;
                  //  playCompleted2 = false;
            }


        } catch (UnsupportedAudioFileException e) {
            // TODO Auto-generated catch block
            e.printStackTrace();
        } catch (LineUnavailableException ex) {
            System.out.println("Audio line for playing back is unavailable.");
            ex.printStackTrace();
        } catch (IOException e) {
            // TODO Auto-generated catch block
            e.printStackTrace();
        }



    }

    public void update(LineEvent event) {
        LineEvent.Type type = event.getType();

        if (type == LineEvent.Type.START) {
            System.out.println("Playback started.");

        } else if (type == LineEvent.Type.STOP) {
            playCompleted1 = true;
            System.out.println("Playback completed.");
           /* if(playCompleted1 == true){
                playCompleted2 = true;
                System.out.println("Playback2 completed.");
            }*/
        }

    }
    public static void convertMsgToAudio(String msg){

        int len = msg.length();
        duration = new long[len];
        msg = msg.toUpperCase();
        System.out.println("Msg 2 : " + msg);

        int i;
        //char ch;
        for(i=0;i<msg.length();i++){

            if(msg.charAt(i) == 'A'){
                duration[i] = 500000;
            }
            else if (msg.charAt(i) == 'B'){
                duration[i] = 510000;
            }
            else if (msg.charAt(i) == 'C'){
                duration[i] = 520000;
            }
            else if (msg.charAt(i) == 'D'){
                duration[i] = 530000;               
            }
            else if (msg.charAt(i) == 'E'){
                duration[i] = 540000;
            }
            else if (msg.charAt(i) == 'F'){
                duration[i] = 550000;
            }
            else if (msg.charAt(i) == 'G'){
                duration[i] = 560000;
            }
            else if (msg.charAt(i) == 'H'){
                duration[i] = 570000;
            }
            else if (msg.charAt(i) == 'I'){
                duration[i] = 580000;
            }
            else if (msg.charAt(i) == 'J'){
                duration[i] = 600000;
            }
            else if (msg.charAt(i) == 'K'){
                duration[i] = 650000;
            }
            else if (msg.charAt(i) == 'L'){
                duration[i] = 660000;
            }
            else if (msg.charAt(i) == 'M'){
                duration[i] = 680000;
            }
            else if (msg.charAt(i) == 'N'){
                duration[i] = 700000;
            }
            else if (msg.charAt(i) == 'O'){
                duration[i] = 750000;
            }
            else if (msg.charAt(i) == 'P'){
                duration[i] = 800000;
            }
            else if (msg.charAt(i) == 'Q'){
                duration[i] = 850000;
            }
            else if (msg.charAt(i) == 'R'){
                duration[i] = 900000;
            }
            else if (msg.charAt(i) == 'S'){
                duration[i] = 950000;
            }
            else if (msg.charAt(i) == 'T'){
                duration[i] = 9800000;
            }
            else if (msg.charAt(i) == 'U'){
                duration[i] = 970000;
            }
            else if (msg.charAt(i) == 'V'){
                duration[i] = 1200000;
            }
            else if (msg.charAt(i) == 'W'){
                duration[i] = 1300000;
            }
            else if (msg.charAt(i) == 'X'){
                duration[i] = 1400000;
            }
            else if (msg.charAt(i) == 'Y'){
                duration[i] = 960000;
            }
            else if (msg.charAt(i) == 'Z'){
                duration[i] = 1600000;
            }
            else if (msg.charAt(i) == ' '){
                duration[i] = 1000000;
            }   
        }
        /*for(i=0;i<duration.length;i++){
            System.out.println(duration[i]);
        }*/
        Stegano s = new Stegano();
        s.convertToAudio();
    }

    public static void main(String[] args) {
        // TODO Auto-generated method stub
        Scanner s = new Scanner(System.in);
        String msg;
        System.out.print("Enter message: ");
        msg = s.nextLine();
        s.close();
        System.out.println("Msg " + msg);
        convertMsgToAudio(msg);
    }

}

请帮忙。我是这个新手

1 个答案:

答案 0 :(得分:1)

这样做你想要的吗?

pos = clip1.getMicrosecondPosition();
System.out.println("pos 1: " + pos);
if( pos == (d + duration[i])){
    System.out.println("posFinal : " + pos);
    clip1.stop();
    break;
}  

当您检查pos == (d + duration[i])时,您假设clip1.getMicrosecondPosition()将始终递增1.如果它增加超过1,它可能会跳过检查并且永远不会终止循环。尝试将该行更改为

if( pos >= (d + duration[i])){

同样可以进一步查看clip2