오디오 클립이로드 될 때까지 기다리는 방법은 무엇입니까?

Dr_Click

저는 JAVA에서 꽤 초보자이고 클립을 읽으려고합니다. 내 코드는 다음과 같습니다.

import java.io.BufferedInputStream;
import java.io.File;
import java.io.FileInputStream;
import java.io.InputStream;

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;

public class TestClipBis {
protected static AudioFormat audioFormat;

public static void main(String[] args) throws Exception {

// Specification of the sound to play
// No control. We assume that the sound can be played on audio system
//File soundFile = new File("chimes.wav");
File soundFile = new File("test.wav");
InputStream is = new FileInputStream(soundFile);
InputStream bufferedIn = new BufferedInputStream(is);
//AudioInputStream sound = AudioSystem.getAudioInputStream(soundFile);
AudioInputStream sound = AudioSystem.getAudioInputStream(bufferedIn);

audioFormat = sound.getFormat();
System.out.println(audioFormat);

// Loading the sound into the memory (a Clip)
DataLine.Info info = new DataLine.Info(Clip.class, sound.getFormat());
System.out.println(info);
//Clip clip = (Clip) AudioSystem.getClip();
Clip clip = (Clip) AudioSystem.getLine(info);

System.out.println("Sound frame lenght : "+sound.getFrameLength());
System.out.println("Clip FrameLength before opening : "+clip.getFrameLength());
System.out.println("Clip will open - "+info);
System.out.println("Info format : "+info.getLineClass());

// Check before this line that everything is in memory
// Yes, but how ?
clip.open(sound);
System.out.println("Clip is open");
System.out.println("Clip FrameLength after opening : "+clip.getFrameLength());
// Due to a bug in Java Sound,
// we explicitly out of the VM when the sounds stop
clip.addLineListener(new LineListener() {
  public void update(LineEvent event) {
    if (event.getType() == LineEvent.Type.STOP) {
        System.out.println("Methode de sortie");
      event.getLine().close();
      System.exit(0);
    }
  }
});


// Playing the clip
clip.start();

System.out.println("IsActive : "+clip.isActive());
//clip.close();

 }
} 

내 문제는 클립을 열고 재생하기 전에 클립이 메모리에로드되었는지 확인하는 방법입니다. 위의 코드를 사용하면 사운드 파일을 열고 재생할 때 몇 초 동안 재생할 수 있지만 동일한 길이, 무작위 및 전체 노래가 전혀 없습니다.

아니면 클립이 아닌 다른 것을 사용하여 노래를 재생해야합니까? 그러나 나는 노래를 처음부터 끝까지 스트리밍하는 것이 아니라 "이동"하고 싶습니다.

편집하다:

좋아, 나는 몇 가지 시도했다. 먼저 "ByteArrayOuptputStream"이 작성되었는지 확인했습니다. 루프에 "println"이 있고 예, 모두 작성되었지만 문제가 해결되지는 않습니다.

그런 다음 클립을 열 때 audioformat, bytearray, startpoint, bufferlength와 같은 매개 변수를 추가하려고했습니다. 더 나은 것은 없습니다.

그러다가 소리가 멈출 때 빠져 나가는 방법이 사용되는 것을 알았습니다. 그래서 나는 그 방법을 (주석 기호로) "음소거"하려고했습니다. 결과는 다릅니다. 파일을 읽었지만 소리가 엉망입니다. CPU 사용량을 확인하면 100 % 정도입니다. 문제가 무엇인지 추측하는 첫 번째 단서입니까?

시작 후 프레임 위치를 나타내는 루프를 만들려고했습니다. 모든 프레임을 읽었지만 소리는 여전히 떨립니다. 나는 또한 시작 방법 전후에 thead.sleep을 시도했습니다.

그래서 여기에 제가 사용하는 코드가 있습니다. 많은 코드 부분이 "주석 따옴표"사이에 있습니다. 시도, 실패했기 때문입니다.

import java.io.ByteArrayInputStream;
import java.io.ByteArrayOutputStream;
import java.io.File;
import java.io.FileInputStream;
import java.nio.ByteBuffer;

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;

public class TestBufferedClip {
protected static AudioFormat audioFormat;
public static ByteBuffer buffer;

public static void main(String[] args) throws Exception {

// Specification of the sound to play
// No control. We assume that the sound can be played on audio system
//File soundFile = new File("chimes.wav");
File soundFile = new File("test.wav");
FileInputStream fis = new FileInputStream(soundFile);

ByteArrayOutputStream baos = new ByteArrayOutputStream((int)soundFile.length());

byte[] buf = new byte[1024];
int n = 0;
int loop = 0;
while ((n=fis.read(buf))>=0) {
    baos.write(buf);
    buf=new byte[1024];
    System.out.println("Loop = "+loop);
    loop+=1;
}
byte[] ba = baos.toByteArray();
System.out.println("ByteArray size : "+ba.length);
ByteArrayInputStream bais = new ByteArrayInputStream(ba);

//AudioInputStream sound = AudioSystem.getAudioInputStream(soundFile);
AudioInputStream sound = AudioSystem.getAudioInputStream(bais);
audioFormat = sound.getFormat();
System.out.println(audioFormat);

// Loading the sound into the memory (a Clip)
DataLine.Info info = new DataLine.Info(Clip.class, sound.getFormat());
System.out.println("Info :"+info);
//Clip clip = (Clip) AudioSystem.getClip();
Clip clip = (Clip) AudioSystem.getLine(info);

System.out.println("Sound frame lenght : "+sound.getFrameLength());
System.out.println("Info format : "+info.getLineClass());

// Check before this line that everything is in memory
// Yes, but how ?
clip.open(audioFormat, ba, 0, ba.length);
//clip.open(sound);
System.out.println("Clip is open");
System.out.println("Clip FrameLength after opening : "+clip.getFrameLength());
// Due to a bug in Java Sound,
// we explicitly out of the VM when the sounds stop
/*
clip.addLineListener(new LineListener() {
  public void update(LineEvent event) {
    if (event.getType() == LineEvent.Type.STOP) {
        System.out.println("Methode de sortie");
      event.getLine().close();
      System.exit(0);
    }
  }
});
*/

// Playing the clip
System.out.println("Before thread sleep");
try {
    Thread.sleep(31000);
} catch (InterruptedException e){
    e.printStackTrace();
}
System.out.println("After thread sleep");

clip.start();

System.out.println("IsActive : "+clip.isActive());
/*
while (clip.isActive()==true) {
    System.out.println("Position = "+clip.getFramePosition());
}
*/
//clip.close();

}
} 

@Phil Freihofner :
"시작"지점에 도달 할 때까지 데이터를 읽고 버리는 솔루션에 대해 생각했습니다. "SourceDataLine을 사용하여 오디오 파일 내의 한 지점에서 시작하려면 원하는 시작 지점에 도달 할 때까지 오디오 입력 라인에서 데이터를 읽고 버려야합니다."라고 썼습니다. 어떻게 하죠? "SourceDataLine"메서드를 사용할 때 시작 메서드는 line.write (bytes, 0, bytesreads); 스피커에서 소리를 가리 킵니다.
그래서, 어떻게 읽고 버리는가? 줄에 "읽기"방법을 찾지 못했습니다.

필 프라이 호프 너

javax.sound.sampled는 오디오 재생을위한 두 개의 객체를 지원합니다. 사용중인 클립은 재생하기 전에 메모리에 완전히로드되어야합니다. 장점으로는 마이크로 초 또는 프레임 위치를 사용하여 클립 내에서 재생을 시작하는 위치를 쉽게 지정할 수 있습니다.

먼저 사운드를 바이트 버퍼에로드해도 이점이 없습니다. 이는 클립에 대한 중복 수준의 버퍼링입니다. DSP 또는 데이터에 도달해야하는 다른 작업을 수행하려는 경우에만 수행합니다. Clip의 기본 제공 기능을 넘어서는 시작 지점을 설정할 수 있습니다.

가능한 오디오 선택을 선택하기 전에 클립으로 미리로드 할 수 있다면 RAM이 부족하지 않는 한 최상의 솔루션 일 수 있습니다.

재생을위한 다른 옵션은 SourceDataLine입니다. 버퍼 단위로 파일을 읽고 재생합니다. 따라서 언로드 된 클립보다 빠르게 시작할 수 있습니다 (먼저 전체 파일을 메모리에로드 할 필요가 없음). 그러나 클립이 미리로드되면 반복적 인 파일로드없이 클립이 재생됩니다.

SourceDataLine을 사용하여 오디오 파일 내의 한 지점에서 시작하려면 원하는 시작 지점에 도달 할 때까지 오디오 입력 라인에서 데이터를 읽고 버려야합니다. 프레임을 계산하여이를 수행 할 수 있습니다 (형식은 프레임 당 바이트 수를 알려줍니다). 이 읽기 및 삭제는 타이밍을 약간 방해 할 수 있지만, 내 경험에 따르면 오디오 데이터를 읽고 버리는 것은 재생보다 몇 배 더 빠릅니다.

Clip 및 SourceDataLine API에 대한 링크가 포함 된 자세한 정보 Java Sound Tutorials확인하십시오 .

다음은 클립로드의 예입니다.

File soundFile = new File("test.wav");
AudioInputStream sound = AudioSystem.getAudioInputStream(soundFile);
DataLine.Info info = new DataLine.Info(Clip.class, sound.getFormat());
Clip clip = (Clip) AudioSystem.getLine(info);
clip.open(sound);

test.wav의 데이터는 이제 RAM에 있어야합니다. 바이트 버퍼와 버퍼링 된 라인을 사용하는 다른 모든 것은 불필요합니다.

재생할 준비가되면 clip.setMicrosecondPosition (long milliseconds)을 사용하여 사운드가 원하는 위치에서 시작되도록 설정합니다 (클립을 이미 재생 한 경우가 아니라면 처음부터 시작하는 경우에는 필요하지 않습니다. 위치는 정지했을 때의 위치입니다). 그런 다음 clip.start ()를 사용하여 재생을 시작합니다.

중요 참고 : 재생을 실행하는 프로그램이 종료되면 재생이 조기에 종료됩니다. 이를 테스트하는 한 가지 방법은 clip.start () 뒤에 Thread.sleep (long milliseconds) 명령을 삽입하는 것입니다. 여기서 milliseconds 값은 클립 길이보다 깁니다. 그러나 이것은 실제 해결책이 아니며 프로그램이 클립 재생 스레드를 닫는 것을 방지하기위한 진단 일뿐입니다. 오디오 재생을 사용하는 스레드가 아닌 기본 스레드에서 프로그램을 계속 실행해야합니다.

이 기사는 인터넷에서 수집됩니다. 재 인쇄 할 때 출처를 알려주십시오.

침해가 발생한 경우 연락 주시기 바랍니다[email protected] 삭제

에서 수정
0

몇 마디 만하겠습니다

0리뷰
로그인참여 후 검토

관련 기사

분류에서Dev

Observable이 완료 될 때까지 기다리는 방법은 무엇입니까?

분류에서Dev

비디오 클립이 Javafx에서 전환 될 때 특수 효과를 페이드 인 및 페이드 아웃하는 방법은 무엇입니까?

분류에서Dev

AngularJS : 모델이 변경 될 때 라디오 버튼보기를 변경하는 방법은 무엇입니까?

분류에서Dev

오디오를 재생하고 다시 재생하기 위해 완료 될 때까지 기다리는 방법은 무엇입니까?

분류에서Dev

Synchron Ajax Call-또는 : 모든 것이로드 될 때까지 기다리는 방법은 무엇입니까?

분류에서Dev

모든 어린이가 마운트 될 때까지 기다리지 않고 일찍 가져 오는 방법은 무엇입니까?

분류에서Dev

내 오디오 입력이 항상 웹캠 마이크가 될 수있는 방법은 무엇입니까?

분류에서Dev

장면이 완전히로드 될 때까지 기다리는 방법은 무엇입니까?

분류에서Dev

Angular 모듈이로드 될 때까지 기다리는 방법은 무엇입니까?

분류에서Dev

컨테이너 뷰의 뷰가로드 될 때까지 기다리는 방법은 무엇입니까?

분류에서Dev

ActionListener가 실행될 때까지 제대로 기다리는 방법은 무엇입니까?

분류에서Dev

복사 프로세스 (cp)가 완료 될 때까지 기다리는 방법은 무엇입니까?

분류에서Dev

조건이 충족 될 때까지 코 루틴을 기다리는 방법은 무엇입니까?

분류에서Dev

Terraform이 cloudinit가 완료 될 때까지 기다리도록하는 방법은 무엇입니까?

분류에서Dev

"onAuthStateChanged"가 "currentUser.updateProfile"이 완료 될 때까지 기다리도록하는 방법은 무엇입니까?

분류에서Dev

팝업이 표시 될 때까지 기다리는 방법은 무엇입니까?

분류에서Dev

모든 가져 오기 프로세스가 node.js에서 완료 될 때까지 사후 처리를 강제하는 방법은 무엇입니까?

분류에서Dev

플렉스 랩이 트리거 될 때 오른쪽으로 정렬하는 방법은 무엇입니까?

분류에서Dev

Python에서로드 될 때까지 기다리지 않고 Selenium WebDriver (Chrome)로 페이지를 여는 방법은 무엇입니까?

분류에서Dev

DotNetBrowser에서 인쇄하기 전에 녹아웃 페이지로드가 완료 될 때까지 기다리는 방법은 무엇입니까?

분류에서Dev

웹 사이트 콘텐츠가 완전히로드 될 때까지 숨기는 방법은 무엇입니까?

분류에서Dev

리소스가로드 될 때까지 기다리는 방법

분류에서Dev

완료 될 때까지 기다리지 않고 세 번째 애플리케이션 스레드를 닫는 선호하는 방법은 무엇입니까?

분류에서Dev

리디렉션 될 때 올바른 이름으로 파일을 얻는 방법은 무엇입니까?

분류에서Dev

Docker-compose Laravel 데이터베이스가로드 될 때까지 기다리는 방법은 무엇입니까?

분류에서Dev

React에서 소품이 변경 될 때 데이터 및 setState를 가져 오는 방법은 무엇입니까?

분류에서Dev

오디오 파일을 재생하기 위해 오디오 경로를 얻는 방법은 무엇입니까?

분류에서Dev

Chrome 사전 렌더링 : 페이지가 실제로로드 될 때까지 자바 스크립트를 연기하는 방법은 무엇입니까?

분류에서Dev

탭이 변경 될 때 데이터를 다시로드하지 않는 방법은 무엇입니까?

Related 관련 기사

  1. 1

    Observable이 완료 될 때까지 기다리는 방법은 무엇입니까?

  2. 2

    비디오 클립이 Javafx에서 전환 될 때 특수 효과를 페이드 인 및 페이드 아웃하는 방법은 무엇입니까?

  3. 3

    AngularJS : 모델이 변경 될 때 라디오 버튼보기를 변경하는 방법은 무엇입니까?

  4. 4

    오디오를 재생하고 다시 재생하기 위해 완료 될 때까지 기다리는 방법은 무엇입니까?

  5. 5

    Synchron Ajax Call-또는 : 모든 것이로드 될 때까지 기다리는 방법은 무엇입니까?

  6. 6

    모든 어린이가 마운트 될 때까지 기다리지 않고 일찍 가져 오는 방법은 무엇입니까?

  7. 7

    내 오디오 입력이 항상 웹캠 마이크가 될 수있는 방법은 무엇입니까?

  8. 8

    장면이 완전히로드 될 때까지 기다리는 방법은 무엇입니까?

  9. 9

    Angular 모듈이로드 될 때까지 기다리는 방법은 무엇입니까?

  10. 10

    컨테이너 뷰의 뷰가로드 될 때까지 기다리는 방법은 무엇입니까?

  11. 11

    ActionListener가 실행될 때까지 제대로 기다리는 방법은 무엇입니까?

  12. 12

    복사 프로세스 (cp)가 완료 될 때까지 기다리는 방법은 무엇입니까?

  13. 13

    조건이 충족 될 때까지 코 루틴을 기다리는 방법은 무엇입니까?

  14. 14

    Terraform이 cloudinit가 완료 될 때까지 기다리도록하는 방법은 무엇입니까?

  15. 15

    "onAuthStateChanged"가 "currentUser.updateProfile"이 완료 될 때까지 기다리도록하는 방법은 무엇입니까?

  16. 16

    팝업이 표시 될 때까지 기다리는 방법은 무엇입니까?

  17. 17

    모든 가져 오기 프로세스가 node.js에서 완료 될 때까지 사후 처리를 강제하는 방법은 무엇입니까?

  18. 18

    플렉스 랩이 트리거 될 때 오른쪽으로 정렬하는 방법은 무엇입니까?

  19. 19

    Python에서로드 될 때까지 기다리지 않고 Selenium WebDriver (Chrome)로 페이지를 여는 방법은 무엇입니까?

  20. 20

    DotNetBrowser에서 인쇄하기 전에 녹아웃 페이지로드가 완료 될 때까지 기다리는 방법은 무엇입니까?

  21. 21

    웹 사이트 콘텐츠가 완전히로드 될 때까지 숨기는 방법은 무엇입니까?

  22. 22

    리소스가로드 될 때까지 기다리는 방법

  23. 23

    완료 될 때까지 기다리지 않고 세 번째 애플리케이션 스레드를 닫는 선호하는 방법은 무엇입니까?

  24. 24

    리디렉션 될 때 올바른 이름으로 파일을 얻는 방법은 무엇입니까?

  25. 25

    Docker-compose Laravel 데이터베이스가로드 될 때까지 기다리는 방법은 무엇입니까?

  26. 26

    React에서 소품이 변경 될 때 데이터 및 setState를 가져 오는 방법은 무엇입니까?

  27. 27

    오디오 파일을 재생하기 위해 오디오 경로를 얻는 방법은 무엇입니까?

  28. 28

    Chrome 사전 렌더링 : 페이지가 실제로로드 될 때까지 자바 스크립트를 연기하는 방법은 무엇입니까?

  29. 29

    탭이 변경 될 때 데이터를 다시로드하지 않는 방법은 무엇입니까?

뜨겁다태그

보관