#java #swing
#java #swing
Вопрос:
В моем приложении swing я использую класс для воспроизведения звука при щелчке мыши. Проблема, с которой я сталкиваюсь, заключается в том, что когда я вызываю класс, звук воспроизводится один раз, и когда внезапно нажимается другая кнопка, звук не воспроизводится. Я пытался ввести задержку в свой код, но идентификатор по-прежнему работает не так, как я ожидал. Это как-то связано с потоками?? Я не силен в потоках, поэтому, пожалуйста, скажите мне, как это сделать. Код, который я использую, выглядит следующим образом,
package utilities;
import java.applet.AudioClip;
import java.io.File;
import java.io.IOException;
import java.io.InputStream;
import java.net.URL;
import java.util.logging.Level;
import java.util.logging.Logger;
import sun.audio.AudioData;
import sun.audio.AudioPlayer;
import sun.audio.AudioStream;
import sun.audio.ContinuousAudioDataStream;
public class Tone {`
File wavFile = new File("sounds/Windows Default.wav");
URL urlClick = Tone.class.getResource("/sounds/WindowsDefault.wav");
AudioClip sound;
public void sound() {
AudioStream as = null;
try {
InputStream in = this.getClass().getResourceAsStream("/sounds/WindowsDefault.wav");
as = new AudioStream(in);
AudioData data = as.getData();
// Create ContinuousAudioDataStream.
ContinuousAudioDataStream cas = new ContinuousAudioDataStream (data);
//System.out.println(as.getLength());
AudioPlayer.player.start(cas);
//System.out.println(urlClick);
//sound = Applet.newAudioClip(urlClick);
//this.wait(1000);
for(int i =0;i<100000;i ){
double k = Math.pow(i, 5);
if(i==99999){
AudioPlayer.player.stop(cas);
return;
}
}
// sound.play();
String relativeDirectory = System.getProperty("user.dir");
System.out.println(relativeDirectory);
} catch (IOException ex) {
Logger.getLogger(Tone.class.getName()).log(Level.SEVERE, null, ex);
} finally {
try {
as.close();
} catch (IOException ex) {
Logger.getLogger(Tone.class.getName()).log(Level.SEVERE, null, ex);
}
}
}
public static void main(String[] args) {
Tone tone = new Tone();
tone.sound();
System.out.println("done");
}
}
—РЕДАКТИРОВАТЬ—
Причина, по которой я использовал continuousaudiostream, заключается в том, что звук вообще не воспроизводился, когда я использую это, чтобы услышать какой-нибудь звук. Даже когда я использовал AudioStream, проблема была там..
Комментарии:
1. Используйте
javax.sound.sampled.Clip
или непосредственноAudioInputStream
вместо того, чтобы углубляться вsun.*
классы.2. когда вы вызываете метод напрямую (вне вашего апплета), можете ли вы заставить звук воспроизводиться два раза?
3. нет, даже когда я вызываю метод напрямую, я иногда не слышу звук.. когда я говорю напрямую, я вызываю из main ()
Ответ №1:
1) Лучше не использовать скрытые классы / api — как вы уже прочитали по ссылке, которую вы получили в своем другом вопросе 🙂
2) остановите / закройте уже запущенный звук перед запуском / повторным открытием снова, в общедоступном api что-то вроде:
Clip clip;
private void doPlay(final String url) {
try {
stopPlay();
AudioInputStream inputStream = AudioSystem
.getAudioInputStream(getClass().getResourceAsStream(url));
clip = AudioSystem.getClip();
clip.open(inputStream);
clip.start();
} catch (Exception e) {
stopPlay();
System.err.println(e.getMessage());
}
}
private void stopPlay() {
if (clip != null) {
clip.stop();
clip.close();
clip = null;
}
}
(Примечание: полностью закрыт только для иллюстрации, доработайте логику, чтобы загрузить один раз, а затем остановить / запустить снова)
Комментарии:
1. я не хочу останавливаться и начинать. на самом деле я просто хочу воспроизводить звук щелчка не более секунды. итак, для каждого клика я хочу воспроизвести это один раз. есть ли какой-либо способ, подобный тому, как после запуска звука при генерации события click следующее событие click не будет снова вызывать метод sound () для воспроизведения . wav-файл?? я так не думаю .. объясните мне, если я был неправ..
2. @Deepak: «на самом деле я просто хочу воспроизводить звук щелчка не более секунды». Изучите
Clip.isRunning()
,Clip.isActive()
LineListener
иjavax.swing.Timer
. Вы обязательно найдете ответ, используя какую-нибудь комбинацию из них.
Ответ №2:
Похоже, что ContinuousAudioDataStream сбрасывается только после достижения конца файла, так что, возможно, второе нажатие кнопки произошло до того, как это произошло. Может быть, попробовать сбросить поток