剪辑不播放任何声音
Posted
技术标签:
【中文标题】剪辑不播放任何声音【英文标题】:Clip not playing any sound 【发布时间】:2013-06-16 23:15:05 【问题描述】:好吧,标题说明了一切,我尝试使用 javax.sound 播放 wav 文件,但没有任何反应。我尝试了许多不同的文件,但没有任何运气。
public static void main(String[] args) throws IOException, UnsupportedAudioFileException, LineUnavailableException
File in = new File("C:\\Users\\Sandra\\Desktop\\music\\rags.wav");
AudioInputStream audioInputStream = Audiosystem.getAudioInputStream(in);
Clip play = AudioSystem.getClip();
play.open(audioInputStream);
FloatControl volume= (FloatControl) play.getControl(FloatControl.Type.MASTER_GAIN);
volume.setValue(1.0f); // Reduce volume by 10 decibels.
play.start();
【问题讨论】:
您是否遇到任何错误或什么也没发生? 查看工作示例***.com/tags/javasound/info 【参考方案1】:如前所述,您需要阻止主线程退出,因为这会导致 JVM 终止。
Clip#start
不是阻塞调用,这意味着它会在调用后(很快)返回。
我毫不怀疑有很多方法可以解决这个问题,这只是其中一种的简单示例。
public class PlayMusic
public static void main(String[] args) throws InterruptedException
Clip play = null;
try
File in = new File("C:\\Users\\Public\\Music\\Sample Music\\Kalimba.wav");
AudioInputStream audioInputStream = AudioSystem.getAudioInputStream(in);
play = AudioSystem.getClip();
play.open(audioInputStream);
FloatControl volume = (FloatControl) play.getControl(FloatControl.Type.MASTER_GAIN);
volume.setValue(1.0f); // Reduce volume by 10 decibels.
play.start();
// Loop until the Clip is not longer running.
// We loop this way to allow the line to fill, otherwise isRunning will
// return false
//do
// Thread.sleep(15);
// while (play.isRunning());
play.drain();
catch (UnsupportedAudioFileException | IOException | LineUnavailableException ex)
ex.printStackTrace();
finally
try
play.close();
catch (Exception exp)
System.out.println("...");
实际的解决方案将取决于您的需求。
【讨论】:
如果没有简单的礼貌来解释原因,您必须欣赏盲目投票,这样我们都可以了解什么会使答案更好 @MadProgrammerClip
是 DataLine
,因此,start()
是非阻塞的。但是,接口中明确指出方法drain()
是阻塞:“此方法阻塞,直到排空完成。”来自DataLine.drain()。任何需要人为阻止程序退出的解决方案都是不正确的。这在Java Playing Back Audio Tutorial 中有明确说明。
@Jared 嗯,很高兴知道 - 此外,每条规则都有例外;)
我在 (1) 带有 JDK 1.8.0_102-b14 64 位的笔记本电脑(Linux Mint 18.0 64 位)和 (2) 运行 Armbian 5.25(内核 3.4.113)的 Orange Pi Zero 上进行了一些测试)与 JDK 1.8.0_121-b13(来自 Oracle)。我发现在 (2)-OrPi drain()
上似乎没有阻塞,而是在阻塞之前执行了System.out.println(...)
(“农民调试”)。不幸的是,在 (1) 笔记本电脑上,情况正好相反,println(...)
使它不阻塞,如果没有它就会阻塞。 (1) 和 (2) 上最可靠的方法是 Thread.sleep(clip.getMicrosecondLength() / 1000)
- 嘿,uggggly...
@fr13d 不得不说我不是drain
的粉丝,我更喜欢用LineListener
,如果你需要的话,你可以用ReentrantLock
或者别的什么来单身剪辑结束【参考方案2】:
Java 的声音Clip
需要一个活动的Thread
来播放音频输入文件,否则应用程序在文件播放之前退出。你可以添加
JOptionPane.showMessageDialog(null, "Click OK to stop music");
拨打start
之后。
【讨论】:
Clip
是 DataLine
,因此,start()
是非阻塞的。但是,接口中明确指出方法drain()
是阻塞:“此方法阻塞,直到排空完成。”来自DataLine.drain()。任何需要人为阻止程序退出的解决方案都是不正确的。这在Java Playing Back Audio Tutorial 中有明确说明。【参考方案3】:
播放音频剪辑的正确方法是按照Playing Back Audio 中的说明排空线路。
所以你的 main 应该是这样的:
public static void main(String[] args) throws IOException,
UnsupportedAudioFileException, LineUnavailableException
File in = new File("C:\\Users\\Sandra\\Desktop\\music\\rags.wav");
AudioInputStream audioInputStream = AudioSystem.getAudioInputStream(in);
Clip play = AudioSystem.getClip();
play.open(audioInputStream);
FloatControl volume= (FloatControl) play.getControl(FloatControl.Type.MASTER_GAIN);
volume.setValue(1.0f); // Reduce volume by 10 decibels.
play.start();
play.drain();
play.close();
play.drain()
阻塞,直到播放完所有数据。
【讨论】:
【参考方案4】:这里playing a clip
public static void main(String[] args) throws Exception
File in = new File("C:\\Users\\Sandra\\Desktop\\music\\rags.wav");
AudioInputStream audioInputStream = AudioSystem.getAudioInputStream(in);
Clip play = AudioSystem.getClip();
play.open(audioInputStream);
FloatControl volume= (FloatControl)play.getControl(FloatControl.Type.MASTER_GAIN);
volume.setValue(1.0f); // Reduce volume by 10 decibels.
play.start();
SwingUtilities.invokeLater(new Runnable()
public void run()
// A GUI element to prevent the Clip's daemon Thread
// from terminating at the end of the main()
JOptionPane.showMessageDialog(null, "Close to exit!");
);
【讨论】:
【参考方案5】:您的程序在播放声音之前终止。我会以某种线程方式执行play.start();
(invokeLater
,...),并找到一种等待声音结束的方法(Reimeus 建议这样做)。
一条线索:
public static void main(String[] args)
javax.swing.SwingUtilities.invokeLater(new Runnable()
public void run()
...
play.start();
JOptionPane.showMessageDialog(null, "Click OK to stop music");
);
【讨论】:
【参考方案6】:如果您只想播放音频,这里有一个方法。
audioFileDirectory
String 变量需要正确的音频文件路径,否则会抛出异常,程序无法运行。
如果使用 IDE,则在项目中拥有正确的音频文件目录的示例:
-
在
src
文件夹中创建一个文件夹,例如:“音乐”并在其中放置一个音频文件
audioFileDirectory = "/music/name_of_audio_file";
播放音频的重要部分是程序的主线程需要以某种方式“活着”,所以行
Thread.sleep(audio.getMicrosecondLength()/1000);
是主线程“活着”的地方,参数audio.getMicrosecondLength()/1000
是“活着”的时间,即音频文件的整个长度。
public class AudioTest
void playAudio() throws Exception
String audioFileDirectory = "your_audioFileDirectory";
InputStream is = getClass().getResourceAsStream(audioFileDirectory);
BufferedInputStream bis = new BufferedInputStream(is);
AudioInputStream ais = AudioSystem.getAudioInputStream(bis);
Clip audio = AudioSystem.getClip();
audio.open(ais);
audio.loop(Clip.LOOP_CONTINUOUSLY);
audio.start();
Thread.sleep(audio.getMicrosecondLength()/1000);
audio.close();
// end playAudio
public static void main(String[] args)
try
new AudioTest().playAudio();
catch (Exception e)
System.out.println("Class: " + e.getClass().getName());
System.out.println("\nMessage:\n" + e.getMessage() + "\n");
e.printStackTrace();
// end main
// end class AudioTest
【讨论】:
以上是关于剪辑不播放任何声音的主要内容,如果未能解决你的问题,请参考以下文章