7

ゲーム中に2つのwavサウンド(バックグラウンドミュージックとエフェクト)を同時に再生しようとしています。私は最初に、サウンドの再生、停止、ループを処理するJavaの別のオーディオハンドラーを使用して、このコードのチャンクを作成しました。このコンストラクトは、バックグラウンドミュージックまたはエフェクトを再生しますが、一度に1つだけ再生します。インターネットを見回して、サウンドを処理するためにjavax.sound.sampled.Clipを使用するように言われたので、同じ構成(再生、停止、ループ)を再利用しましたが、javax.sound.sampled.Clipを使用するように切り替えました。今、私は完全に迷子になっています。これまで読んだことから、すべてを正しく実行し、Eclipseエディターでエラーは発生しませんでしたが、実行すると、2つのエラーのうちの1つが発生します。eclipse(Linuxで実行)では、LineUnavailableExceptionがスローされます。Eclipse(Windows 7で実行)では、このコードのloop()セクションでjava.lang.NullPointerExceptionが発生します。私が間違っていることを教えてくれるか、関連するドキュメントを教えていただければ幸いです。例外を処理するコードで何かを想定していますが、よくわかりません。他の恐ろしいコードの失敗を見つけた場合は、私ができる限り最高のプログラマーになるように努力していることを知らせてください。建設的な批判に本当に感謝しています。お時間をいただきありがとうございます。

    import java.io.File;
    import java.io.IOException;
    import java.net.MalformedURLException;
    import javax.sound.sampled.AudioInputStream;
    import javax.sound.sampled.AudioSystem;
    import javax.sound.sampled.Clip;
    import javax.sound.sampled.LineUnavailableException;
    import javax.sound.sampled.UnsupportedAudioFileException;

    /**
     * Handles play, pause, and looping of sounds for the game.
     * @author Tyler Thomas
     *
     */
    public class Sound {
        private Clip myClip;
        public Sound(String fileName) {
                try {
                    File file = new File(fileName);
                    if (file.exists()) {
                        Clip myClip = AudioSystem.getClip();
                        AudioInputStream ais = AudioSystem.getAudioInputStream(file.toURI().toURL());
                        myClip.open(ais);
                    }
                    else {
                        throw new RuntimeException("Sound: file not found: " + fileName);
                    }
                }
                catch (MalformedURLException e) {
                    throw new RuntimeException("Sound: Malformed URL: " + e);
                }
                catch (UnsupportedAudioFileException e) {
                    throw new RuntimeException("Sound: Unsupported Audio File: " + e);
                }
                catch (IOException e) {
                    throw new RuntimeException("Sound: Input/Output Error: " + e);
                }
                catch (LineUnavailableException e) {
                    throw new RuntimeException("Sound: Line Unavailable: " + e);
                }
        }
        public void play(){
            myClip.setFramePosition(0);  // Must always rewind!
            myClip.loop(0);
            myClip.start();
        }
        public void loop(){
            myClip.loop(Clip.LOOP_CONTINUOUSLY);
        }
        public void stop(){
            myClip.stop();
        }
    }
4

2 に答える 2

16

コードを機能させることができ、クリップについての理解が深まりました。私を最も助けてくれたページはhttp://www3.ntu.edu.sg/home/ehchua/programming/java/J8c_PlayingSound.htmlでした。それはすべてを分解し、どこで間違いを犯したかを知るのに役立ちました。これが私の最終的な作業コードです。以前と同じように、ロジックやスタイルにひどいエラーや見落としがある場合は、お知らせください。

import java.io.File;
import java.io.IOException;
import java.net.MalformedURLException;
import javax.sound.sampled.AudioInputStream;
import javax.sound.sampled.AudioSystem;
import javax.sound.sampled.Clip;
import javax.sound.sampled.LineUnavailableException;
import javax.sound.sampled.UnsupportedAudioFileException;

/**
 * Handles playing, stoping, and looping of sounds for the game.
 * @author Tyler Thomas
 *
 */
public class Sound {
    private Clip clip;
    public Sound(String fileName) {
        // specify the sound to play
        // (assuming the sound can be played by the audio system)
        // from a wave File
        try {
            File file = new File(fileName);
            if (file.exists()) {
                AudioInputStream sound = AudioSystem.getAudioInputStream(file);
             // load the sound into memory (a Clip)
                clip = AudioSystem.getClip();
                clip.open(sound);
            }
            else {
                throw new RuntimeException("Sound: file not found: " + fileName);
            }
        }
        catch (MalformedURLException e) {
            e.printStackTrace();
            throw new RuntimeException("Sound: Malformed URL: " + e);
        }
        catch (UnsupportedAudioFileException e) {
            e.printStackTrace();
            throw new RuntimeException("Sound: Unsupported Audio File: " + e);
        }
        catch (IOException e) {
            e.printStackTrace();
            throw new RuntimeException("Sound: Input/Output Error: " + e);
        }
        catch (LineUnavailableException e) {
            e.printStackTrace();
            throw new RuntimeException("Sound: Line Unavailable Exception Error: " + e);
        }

    // play, stop, loop the sound clip
    }
    public void play(){
        clip.setFramePosition(0);  // Must always rewind!
        clip.start();
    }
    public void loop(){
        clip.loop(Clip.LOOP_CONTINUOUSLY);
    }
    public void stop(){
            clip.stop();
        }
    }
于 2012-08-16T03:28:15.847 に答える
3

音を止めるのに便利なテクニックを見つけました。これらの2つのクラスをコピーして、自分でテストすることができます。それでも、clip.stop()メソッドは一時停止メソッドに近いものです。はい、サウンドの再生を停止しますが、ラインからサウンドをクリアしません。その結果、サウンドはまだ再生キューに入れられており、新しいサウンドを再生することはできません。したがって、clip.close()メソッドを使用すると、このキューに入れられたデータがクリアされ、新しいサウンドを再生したり、別のアクションを実行したりできるようになります。また、次のコードでは、サウンドファイルが「predator.wav」というプロジェクトフォルダに配置されていることに注意してください。このサウンドは、選択したサウンドの代わりに使用する任意のタイプのサウンドにすることができますが、.wav形式であることを確認してください。サウンドは、プロジェクトフォルダの最上位層にある必要があります。

/*
 * File: KeyMap.java
 * Author: Andrew Peturis Chaselyn Langley; UAB EE Students
 * Assignment:  SoundBox - EE333 Fall 2015
 * Vers: 1.0.0 10/20/2015 agp - initial coding
 *
 * Credits: Dr. Green, UAB EE Engineering Professor
 */

import java.io.File;
import java.io.IOException;
import javax.sound.sampled.AudioSystem;
import javax.sound.sampled.Clip;
import javax.sound.sampled.LineUnavailableException;
import javax.sound.sampled.UnsupportedAudioFileException;

public class KeyMap {

    private char keyCode;
    private String song;
    private Clip clip;

    // Don't allow default constructor
    private KeyMap() {
    }

    public KeyMap(char keyCode, String song) throws LineUnavailableException {
        this.keyCode = keyCode;
        this.song = song;

        // Create an audiostream from the inputstream
        clip = AudioSystem.getClip();
    }

    public boolean match(char key) {
        return key == keyCode;
    }

    // Play a sound using javax.sound and Clip interface
    public String play() {
        try {
            // Open a sound file stored in the project folder
            clip.open(AudioSystem.getAudioInputStream(new File(song + ".wav")));

            // Play the audio clip with the audioplayer class
            clip.start();

            // Create a sleep time of 2 seconds to prevent any action from occuring for the first
            // 2 seconds of the sound playing
            Thread.sleep(2000);

        } catch (LineUnavailableException | UnsupportedAudioFileException | IOException | InterruptedException e) {
            System.out.println("Things did not go well");
            System.exit(-1);
        }
        return song;
    }

    // Stop a sound from playing and clear out the line to play another sound if need be.
    public void stop() {
        // clip.stop() will only pause the sound and still leave the sound in the line
        // waiting to be continued. It does not actually clear the line so a new action could be performed.
        clip.stop();

        // clip.close(); will clear out the line and allow a new sound to play. clip.flush() was not 
        // used because it can only flush out a line of data already performed.
        clip.close();
    }
}

/*
 * File: SoundBox.java
 * Author: Andrew Peturis, Chaselyn Langley; UAB EE Students
 * Assignment:  GUI SoundBox - EE333 Fall 2015
 * Vers: 1.0.0 09/08/2015 agp - initial coding
 */

import java.io.BufferedReader;
import java.io.IOException;
import java.io.InputStream;
import java.io.InputStreamReader;
import java.util.Scanner;
import javax.sound.sampled.LineUnavailableException;

/**
 *
 * @author Andrew Peturis, Chaselyn Langley
 *
 */
public class SoundBox {

    static Scanner scanner = new Scanner(System.in);   //Scanner object to read user input
    InputStream input;

    /**
     * @param args the command line arguments
     * @throws java.io.IOException
     */
    public static void main(String[] args) throws IOException, LineUnavailableException {

        String line;
        Character firstChar;
        String predator = "predator";
        String explosion = "explosion";

        BufferedReader br = new BufferedReader(new InputStreamReader(System.in));

        KeyMap[] keyedSongs = {
            new KeyMap('a', predator),};

        while (true) {
            line = br.readLine();
            firstChar = line.charAt(0);

            for (int i = 0; i < keyedSongs.length; i++) {
                if (keyedSongs[i].match(firstChar)) {

                    // Notice now by running the code, after the first second of sleep time the sound can
                    // and another sound can be played in its place
                    keyedSongs[i].stop();
                    System.out.println("Played the sound: " + keyedSongs[i].play());
                    break;
                }
            }

            if (firstChar == 'q') {
                break;
            }
        }
    }
}
于 2015-12-09T17:33:12.610 に答える