Package net.sf.jiga.xtended.impl

Source Code of net.sf.jiga.xtended.impl.SoundInput

package net.sf.jiga.xtended.impl;

import java.applet.Applet;
import java.applet.AudioClip;
import java.io.*;
import java.net.URL;
import java.nio.ByteBuffer;
import java.nio.FloatBuffer;
import java.security.AccessControlContext;
import java.security.AccessController;
import java.security.PrivilegedAction;
import java.util.Collections;
import java.util.HashMap;
import java.util.Map;
import java.util.SortedMap;
import javazoom.jl.decoder.JavaLayerException;
import javazoom.jl.player.Player;
import net.sf.jiga.xtended.JXAException;
import net.sf.jiga.xtended.impl.game.RenderingScene;
import net.sf.jiga.xtended.impl.game.RenderingSceneComponent;
import net.sf.jiga.xtended.impl.game.gl.GLHandler;
import net.sf.jiga.xtended.impl.game.gl.MemScratch;
import net.sf.jiga.xtended.impl.game.gl.RenderingSceneGL;
import net.sf.jiga.xtended.impl.game.gl.SndScratch;
import net.sf.jiga.xtended.impl.system.BufferIO;
import net.sf.jiga.xtended.kernel.*;
import org.lwjgl.openal.AL;
import org.lwjgl.openal.AL10;
import org.lwjgl.openal.OpenALException;
import org.lwjgl.openal.Util;
import org.lwjgl.util.WaveData;

/**
* The SoundInput class implements the Sound interface for playing sounds of
* many supported formats. The MPEG-Layer 3 can be used to decode mp3 encoded
* sound files. The whole class is thread-safe. More information about JLayer,
* the Java MPEG-Layer 3 codec can be found at <a
* href="http://www.javazoom.net/javalayer/javalayer.html"/> JavaZoom.net</a>.
* OpenAL Soft is also supported. To change the sound-config, browse to the
* net/sf/jiga/impl/game/rendering.properties file !
*
* @author www.b23prodtm.info
*/
public class SoundInput implements Sound, Resource, RenderingSceneComponent {

    /** link to all of the openAL scratch (only if openAL is enabled)*/   
    public final static SndScratch sTex = GLHandler.sSnd;
    /**
     * global mute sound
     *
     * @default false
     */
    public static boolean _mute = false;
    /**
     * hash-code
     */
    long hash = System.nanoTime();

    /**
     * returns the unique hash-code for this instance
     *
     * @return the unique hash-code for this instance
     */
    @Override
    public int hashCode() {
        return (int) hash;
    }

    /**
     * returns true or false, whether the specified Object is equal or not to
     * this instance, resp.
     *
     * @param o the Object to compare this instance to
     * @return true or false, whether this instance is equal or not to the
     * specfied Object
     * @see #hashCode()
     */
    @Override
    public boolean equals(Object o) {
        return o == null ? false : o.hashCode() == hashCode();
    }
    /*
     * Position of the sources sound.
     */
    FloatBuffer sourcePos = BufferIO._wrapf(new float[]{0.0f, 0.0f, 0.0f});

    /*
     * Velocity of the sources sound.
     */
    FloatBuffer sourceVel = BufferIO._wrapf(new float[]{0.0f, 0.0f, 0.0f});

    /*
     * Position of the listener.
     */
    FloatBuffer listenerPos = BufferIO._wrapf(new float[]{0.0f, 0.0f, 0.0f});

    /*
     * Velocity of the listener.
     */
    FloatBuffer listenerVel = BufferIO._wrapf(new float[]{0.0f, 0.0f, 0.0f});

    /*
     * Orientation of the listener. (first 3 elements are "at", second 3 are "up")
     */
    FloatBuffer listenerOri = BufferIO._wrapf(new float[]{0.0f, 0.0f, -1.0f, 0.0f, 1.0f, 0.0f});

    /**
     * this is the velocity to add to the AL source
     *
     * @return the velocity added to the AL source 3D-location
     */
    public FloatBuffer getSourceVel() {
        return sourceVel;
    }

    /**
     * the position of the source
     *
     * @return the 3D position of the source
     */
    public FloatBuffer getSourcePos() {
        return sourcePos;
    }

    /**
     * the listener's velocity
     *
     * @return the listener's velocity to add to the listener 3D location
     */
    public FloatBuffer getListenerVel() {
        return listenerVel;
    }

    /**
     * the listener's position
     *
     * @return the listener's 3D-location
     */
    public FloatBuffer getListenerPos() {
        return listenerPos;
    }

    /**
     * the listener orientation
     *
     * @return the listener's 3D orientation vector
     */
    public FloatBuffer getListenerOri() {
        return listenerOri;
    }

    /**
     * sets up the listener's velocity
     *
     * @param listenerVel a float array with a 3D vector for the velocity
     */
    public void setListenerVel(FloatBuffer listenerVel) {
        this.listenerVel = listenerVel;
    }

    /**
     * sets up the listener's position
     *
     * @param listenerPos a float array with a 3D point for the location
     */
    public void setListenerPos(FloatBuffer listenerPos) {
        this.listenerPos = listenerPos;
    }

    /**
     * sets up the source velocity
     *
     * @param sourceVel a float array with the 3D vector for the velocity
     */
    public void setSourceVel(FloatBuffer sourceVel) {
        this.sourceVel = sourceVel;
    }

    /**
     * sets up the listener orientation
     *
     * @param listenerOri a float array with a 3D vector for the orientation
     */
    public void setListenerOri(FloatBuffer listenerOri) {
        this.listenerOri = listenerOri;
    }

    /**
     * sets up the source position
     *
     * @param sourcePos a float array with a 3D vector for the source location
     */
    public void setSourcePos(FloatBuffer sourcePos) {
        this.sourcePos = sourcePos;
    }
    /**
     * is set true or false to enable or disable the openAL library (3D surround
     * sound fx) in the {@linkplain RenderingScene#rb ResourceBundle}
     */
    public static boolean openALEnabled = Boolean.parseBoolean(RenderingScene.rb.getString("openALEnabled"));

    static {
        if (openALEnabled) {
            AccessController.doPrivileged(new PrivilegedAction() {
                @Override
                public Object run() {
                    Runtime.getRuntime().addShutdownHook(new Thread(new Runnable() {
                                @Override
                        public void run() {
                            if (AL.isCreated()) {
                                _killAL();
                            }
                        }
                    }));
                    return null;
                }
            });
        }
    }
    final static BitStack bits = new BitStack();
    final static int SND_INTERFACE_BIT = bits._newBitRange();
    final static int SND_INTERFACE_APPLET = bits._newBit(SND_INTERFACE_BIT);
    final static int SND_INTERFACE_JLAYER = bits._newBit(SND_INTERFACE_BIT);
    final static int SND_INTERFACE_OPENAL = bits._newBit(SND_INTERFACE_BIT);
    final static int SND_STATE_BIT = bits._newBitRange();
    final static int SND_STATE_STOPPED = bits._newBit(SND_STATE_BIT);
    final static int SND_STATE_PLAYING = bits._newBit(SND_STATE_BIT);
    final static int SND_STATE_CLEARED = bits._newBit(SND_STATE_BIT);
    final static int SND_EXT_BIT = bits._newBitRange();
    final static int SND_EXT_LOOP = bits._newBit(SND_EXT_BIT);
    final static int SND_EXT_INRSRC = bits._newBit(SND_EXT_BIT);
    final static int SND_EXT_MUTE = bits._newBit(SND_EXT_BIT);
    private int soundState = SND_STATE_CLEARED | (openALEnabled ? SND_INTERFACE_OPENAL : SND_INTERFACE_APPLET) | SND_EXT_INRSRC;
    /**
     * the current AudioClip instance
     */
    AudioClip bgSfx = null;
    /**
     * the current JLayer player instance
     */
    Player player = null;
    /**
     * the current file resource name
     */
    String fileRsrc = null;

    /**
     * returns true or false, whether this intance is playing a sound or not,
     * resp.
     *
     * @return true or false, whether this instance is playing a sound or not,
     * resp.
     */
    public boolean isPlaying() {
        return (soundState & bits._getMask(SND_STATE_BIT) & SND_STATE_PLAYING) != 0;
    }

    /**
     * dis/enables the JLayer
     *
     * @param b dis/enables the JLayer
     */
    public void setUseJLayerEnabled(boolean b) {
        if (isUseJLayerEnabled() != b) {
            clearResource();
        }
        switchState(SND_INTERFACE_BIT, b ? SND_INTERFACE_JLAYER : openALEnabled ? SND_INTERFACE_OPENAL : SND_INTERFACE_APPLET);
    }

    private void switchState(int optionRange, int state) {
        soundState = soundState - (soundState & bits._getMask(optionRange)) | state;
    }

    private void addExtState(int ext) {
        soundState |= ext;
    }

    private void removeExtState(int ext) {
        soundState = soundState - (soundState & bits._getMask(SND_EXT_BIT) & ext);
    }
    /**
     * the synch-monitor for this instance
     */
    private ThreadGroup soundTG = new ThreadGroup("Sound Input-TG");
    /**
     * the cache for all loaded sound file datas
     */
    protected final static SpritesCacheManager<String, Map<String, Serializable>> _ALBackBuffer = new SpritesCacheManager<String, Map<String, Serializable>>();
    static boolean initAL = true;

    private static void _loadAL() {
        if (openALEnabled && initAL) {
            _ALBackBuffer.setCompressionEnabled(true);
            _ALBackBuffer.setSwapDiskEnabled(true);
            initAL = false;
            int scratchCapacity = Integer.parseInt(RenderingScene.rb.getString("_ALBufferCapacity"));
            GLHandler.sSnd.b.genVRAMBuffersMap(scratchCapacity);
            GLHandler.sSnd.s.genVRAMBuffersMap(scratchCapacity);
        }
    }
    /**
     * the cache of the loaded sound files
     */
    public final static SortedMap<String, Map<String, Serializable>> _ALCache = Collections.synchronizedSortedMap(_ALBackBuffer);

    private static JXAException _getALNoRsrcEx(String fileRsrc) {
        return new JXAException(JXAException.LEVEL.APP, "No such buffer has been loaded before, cannot create openAL source : " + fileRsrc);
    }

    private Player newJLayer(String filename) throws FileNotFoundException, JavaLayerException {
        return new Player(new BufferedInputStream(isInnerResourceModeEnabled() ? getClass().getResourceAsStream(filename) : new FileInputStream(filename)));
    }
    /**
     *
     */
    protected AccessControlContext acc = AccessController.getContext();

    /**
     * loads up the specified file resource (.WAV only for
     * {@linkplain #setHardwareAccel(boolean) openAL}, .MP3 for
     * {@linkplain #setUseJLayerEnabled(boolean) JLayer})
     *
     * @param filename the file resource
     * @return true or false, whether the resource could be loaded or not, resp.
     * @see Class#getResource(String)
     * @see Applet#newAudioClip(URL)
     */
    @Override
    public boolean load(final String filename) {
        return AccessController.doPrivileged(new PrivilegedAction<Boolean>() {
                    @Override
            public Boolean run() {
                return _load(filename);
            }
        }, acc);
    }

    private boolean _load(String filename) {
        if (filename == null || new String("").equals(filename) || isPlaying()) {
            return false;
        }
        if (isResourceLoaded()) {
            clearResource();
        }
        boolean loaded = false;
        try {
            URL rsrc = getClass().getResource(filename);
            File file = new File(filename);
            if (rsrc == null && !file.exists()) {
                loaded = false;
            } else {
                if (JXAenvUtils._debug) {
                    System.err.print("SoundInput loads " + filename);
                }
                if ((soundState & bits._getMask(SND_INTERFACE_BIT) & SND_INTERFACE_APPLET) != 0) {
                    bgSfx = Applet.newAudioClip(isInnerResourceModeEnabled() ? rsrc : file.toURI().toURL());
                    loaded = true;
                    if (JXAenvUtils._debug) {
                        System.err.println(" applet sound");
                    }
                }
                if ((soundState & bits._getMask(SND_INTERFACE_BIT) & SND_INTERFACE_JLAYER) != 0) {
                    player = newJLayer(filename);
                    loaded = true;
                    if (JXAenvUtils._debug) {
                        System.err.println(" jlayer sound");
                    }
                }
                if ((soundState & bits._getMask(SND_INTERFACE_BIT) & SND_INTERFACE_OPENAL) != 0) {
                    WaveData waveFile = null;
                    Map<String, Serializable> map = null;
                    if (!_ALCache.containsKey(filename)) {
                        waveFile = WaveData.create(new BufferedInputStream(isInnerResourceModeEnabled() ? getClass().getResourceAsStream(filename) : new FileInputStream(file)));
                        map = new HashMap<String, Serializable>();
                        if (waveFile != null) {
                            map.put("data", new BufferIO(waveFile.data));
                            map.put("format", waveFile.format);
                            map.put("samplerate", waveFile.samplerate);
                            waveFile.dispose();
                            loaded = true;
                            _ALCache.put(filename, map);
                            if (JXAenvUtils._debug) {
                                System.err.println(" openAL sound");
                            }
                        }
                    } else {
                        loaded = true;
                    }
                }
            }
        } catch (Exception ex) {
            loaded = false;
            throw new JXAException(ex);
        } finally { /* run even after a thrown exception !!*/
            fileRsrc = filename;
            if (loaded) {
                switchState(SND_STATE_BIT, SND_STATE_STOPPED);
                if (JXAenvUtils._debug) {
                    System.err.println(toString() + " has been loaded.");
                }
            } else {
                if (JXAenvUtils._debug) {
                    System.err.println(toString() + " no data has been loaded.");
                }
                switchState(SND_STATE_BIT, SND_STATE_CLEARED);
            }
            return loaded;
        }
    }

    @Override
    public String toString() {
        return "SoundInput " + fileRsrc + " (hash " + hashCode() + ")";
    }

    /**
     * returns the file path resource of this sound
     *
     * @return the file path resource of this sound
     */
    public String getFileRsrc() {
        return fileRsrc;
    }

    private void loadALBuffer() {
        if (_ALCache.containsKey(fileRsrc)) {
            int buffer = GLHandler.sSnd.b.getVRAMFindVacant(), source = GLHandler.sSnd.s.getVRAMFindVacant();
            Map<String, Serializable> waveFile = _ALCache.get(fileRsrc);
            AL10.alBufferData(buffer, (Integer) waveFile.get("format"), (ByteBuffer) ((BufferIO) waveFile.get("data")).getData(), (Integer) waveFile.get("samplerate"));
            Util.checkALError();
            AL10.alSourcei(source, AL10.AL_BUFFER, buffer);
            AL10.alSourcef(source, AL10.AL_PITCH, 1.0f);
            AL10.alSourcef(source, AL10.AL_GAIN, 1.0f);
            AL10.alSource(source, AL10.AL_POSITION, sourcePos);
            AL10.alSource(source, AL10.AL_VELOCITY, sourceVel);
            Util.checkALError();
            AL10.alListener(AL10.AL_POSITION, listenerPos);
            AL10.alListener(AL10.AL_VELOCITY, listenerVel);
            AL10.alListener(AL10.AL_ORIENTATION, listenerOri);
            Util.checkALError();
            GLHandler.sSnd.b.addItem(hashCode(), new MemScratch.Item(buffer, BufferIO._new(0)));
            GLHandler.sSnd.s.addItem(hashCode(), new MemScratch.Item(buffer, BufferIO._newf(0)));
        } else {
            throw _getALNoRsrcEx(fileRsrc);
        }
    }

    /**
     * starts playing the sound in a loop <u>in a separate Thread</u>.
     */
    private void loop() {
        switchState(SND_STATE_BIT, SND_STATE_PLAYING);
        if (JXAenvUtils._debug) {
            System.out.println(toString() + " loop playback");
        }
        getMuteThread().start();
        if ((soundState & bits._getMask(SND_INTERFACE_BIT) & SND_INTERFACE_JLAYER) != 0) {
            Thread t_mp3 = new Thread(soundTG, new Runnable() {
                @Override
                public void run() {
                    try {
                        if (JXAenvUtils._debug) {
                            System.out.println(toString() + " mp3 playback");
                        }
                        while (isPlaying()) {
                            if (player instanceof Player) {
                                if (!isMute()) {
                                    player.play();
                                    player.close();
                                    player = newJLayer(fileRsrc);
                                }
                            } else {
                                break;
                            }
                        }
                    } catch (Exception ex) {
                        throw new JXAException(ex);
                    }
                }
            }, "T-loop-mp3");
            t_mp3.setPriority(Thread.MAX_PRIORITY);
            t_mp3.start();
        }
        if ((soundState & bits._getMask(SND_INTERFACE_BIT) & SND_INTERFACE_APPLET) != 0) {
            if (bgSfx instanceof AudioClip) {
                if (!isMute()) {
                    bgSfx.loop();
                }
            }
        }
        if ((soundState & bits._getMask(SND_INTERFACE_BIT) & SND_INTERFACE_OPENAL) != 0) {
            AL10.alSourcei(GLHandler.sSnd.s.firstItemBufferName(SoundInput.this.hashCode()), AL10.AL_LOOPING, AL10.AL_TRUE);
            if (!isMute()) {
                AL10.alSourcePlay(GLHandler.sSnd.s.firstItemBufferName(SoundInput.this.hashCode()));
            }
        }
    }

    private Thread getMuteThread() {
        Thread t = new Thread(soundTG, new Runnable() {
            @Override
            public void run() {
                if (!isRepeatEnabled()) {
                    return;
                }
                while (isPlaying()) {
                    if (isMute()) {
                        stop();
                    }
                    Thread.yield();
                }
                if (isRepeatEnabled()) {
                    while (isMute() && !isPlaying()) {
                        Thread.yield();
                    }
                    if (!isPlaying()) {
                        loop();
                    }
                }
            }
        }, toString() + "-muteMonitor");
        t.setPriority(Math.max(Thread.MIN_PRIORITY, Thread.currentThread().getPriority() - 1));
        return t;
    }

    /**
     * starts playing te sound <u>in a separate Thread</u>.
     */
    @Override
    public void play() {
        assert fileRsrc != null : "Sound : you must call load(String) once before to play the Sound";
        if (!isResourceLoaded()) {
            if (!load(fileRsrc)) {
                return;
            }
        }
        if ((soundState & bits._getMask(SND_INTERFACE_BIT) & SND_INTERFACE_OPENAL) != 0) {
            try {
                loadALBuffer();
            } catch (OpenALException ex) {
                throw new JXAException(ex);
            }
        }
        if (isRepeatEnabled()) {
            loop();
        } else {
            if (JXAenvUtils._debug) {
                System.out.println(toString() + " playback");
            }
            final Thread tmute = getMuteThread();
            if ((soundState & bits._getMask(SND_INTERFACE_BIT) & SND_INTERFACE_JLAYER) != 0) {
                Thread t_mp3 = new Thread(soundTG, new Runnable() {
                                    @Override
                    public void run() {
                        try {
                            if (player instanceof Player) {
                                if (JXAenvUtils._debug) {
                                    System.out.println(toString() + " mp3 playback");
                                }
                                switchState(SND_STATE_BIT, SND_STATE_PLAYING);
                                tmute.start();
                                if (!isMute()) {
                                    player.play();
                                    stop();
                                }
                            }
                        } catch (JavaLayerException ex) {
                            throw new JXAException(ex);
                        }
                    }
                }, "T-play-mp3");
                t_mp3.setPriority(Thread.MAX_PRIORITY);
                t_mp3.start();
            }
            if ((soundState & bits._getMask(SND_INTERFACE_BIT) & SND_INTERFACE_APPLET) != 0) {
                if (bgSfx instanceof AudioClip) {
                    switchState(SND_STATE_BIT, SND_STATE_PLAYING);
                    tmute.start();
                    if (!isMute()) {
                        bgSfx.play();
                    }
                }
            }
            if ((soundState & bits._getMask(SND_INTERFACE_BIT) & SND_INTERFACE_OPENAL) != 0) {
                switchState(SND_STATE_BIT, SND_STATE_PLAYING);
                AL10.alSourcei(GLHandler.sSnd.s.firstItemBufferName(SoundInput.this.hashCode()), AL10.AL_LOOPING, AL10.AL_FALSE);
                tmute.start();
                if (!isMute()) {
                    AL10.alSourcePlay(GLHandler.sSnd.s.firstItemBufferName(SoundInput.this.hashCode()));
                }
            }
        }
    }

    /**
     *
     * @return
     */
    public boolean isMute() {
        return _mute || (soundState & bits._getMask(SND_EXT_BIT) & SND_EXT_MUTE) != 0;
    }

    /**
     *
     */
    public void mute() {
        addExtState(SND_EXT_MUTE);
    }

    /**
     *
     */
    public void unmute() {
        removeExtState(SND_EXT_MUTE);
    }

    /**
     * stops the current playing sound
     */
    @Override
    public void stop() {
        if ((soundState & bits._getMask(SND_STATE_BIT) & SND_STATE_PLAYING) != 0) {
            if ((soundState & bits._getMask(SND_INTERFACE_BIT) & SND_INTERFACE_JLAYER) != 0) {
                if (player instanceof Player) {
                    player.close();
                }
                switchState(SND_STATE_BIT, SND_STATE_STOPPED);
            }
            if ((soundState & bits._getMask(SND_INTERFACE_BIT) & SND_INTERFACE_APPLET) != 0) {
                if (bgSfx instanceof AudioClip) {
                    bgSfx.stop();
                }
                switchState(SND_STATE_BIT, SND_STATE_STOPPED);
            }
            if ((soundState & bits._getMask(SND_INTERFACE_BIT) & SND_INTERFACE_OPENAL) != 0) {
                AL10.alSourceStop(GLHandler.sSnd.s.firstItemBufferName(SoundInput.this.hashCode()));
                switchState(SND_STATE_BIT, SND_STATE_STOPPED);
            }
        }
    }

    /**
     * returns true or false, whether the JLayer is enabled or not, resp.
     *
     * @return true or false, whether the JLayer is enabled or not, resp.
     */
    public boolean isUseJLayerEnabled() {
        return (soundState & bits._getMask(SND_INTERFACE_BIT) & SND_INTERFACE_JLAYER) != 0;
    }

    @Override
    public void setRepeatEnabled(boolean b) {
        if (b) {
            addExtState(SND_EXT_LOOP);
        } else {
            removeExtState(SND_EXT_LOOP);
        }
    }

    @Override
    public boolean isRepeatEnabled() {
        return (soundState & bits._getMask(SND_EXT_BIT) & SND_EXT_LOOP) != 0;
    }

    /**
     * instances a new SoundInput
     */
    public SoundInput() {
        this("", true);
    }

    /**
     * instances a new SoundInput
     *
     * @param filePath the file resource for the sound (.aif, .wav, .mp3--Jlayer
     * must be enabled--is supported)
     * @param innerResource tells whether to look for the file in the classpath
     * or the absolute path
     */
    public SoundInput(String filePath, boolean innerResource) {
        ThreadWorks.prioritizeThreadGroups(ThreadWorks.securityTWKS.workTG, soundTG);
        fileRsrc = filePath;
        setInnerResourceModeEnabled(innerResource);
        _loadAL();
    }

    /**
     *
     * @return
     */
    @Override
    public Object loadResource() {
        return load(fileRsrc);
    }

    /**
     * 1) Releases all sources. 2) Releases all buffers. 3) destroys openAL.
     */
    private static void _killAL() {
        if (initAL) {
            GLHandler.sSnd.s.freeScratch();
            GLHandler.sSnd.b.freeScratch();
            AL.destroy();
        }
    }

    @Override
    protected void finalize() throws Throwable {
        super.finalize();
        clearResource();
    }

    /**
     * clears the current SoundInput resources. NOTICE : it seems that openAL,
     * unlike openGL, does NOT provide a perfect target-resource management, so
     * that a deletedSource cannot be reused again at the same address. Avoiding
     * to use this method is preferred.
     *
     * @return
     */
    @Override
    public Object clearResource() {
        if (!isResourceLoaded()) {
            return null;
        }
        stop();
        if (player instanceof Player) {
            player = null;
        }
        if (bgSfx instanceof AudioClip) {
            bgSfx = null;
        }
        GLHandler.sSnd.s.discardItems((RenderingSceneGL)rsc, hashCode());
        GLHandler.sSnd.b.discardItems((RenderingSceneGL)rsc, hashCode());
        switchState(SND_STATE_BIT, SND_STATE_CLEARED);
        return null;
    }

    /**
     *
     * @return
     */
    @Override
    public boolean isResourceLoaded() {
        return (soundState & bits._getMask(SND_STATE_BIT) & SND_STATE_CLEARED) == 0;
    }

    /**
     * @return
     */
    public boolean isInnerResourceModeEnabled() {
        return (soundState & bits._getMask(SND_EXT_BIT) & SND_EXT_INRSRC) != 0;
    }

    /**
     * @param b
     */
    public final void setInnerResourceModeEnabled(boolean b) {
        if (b) {
            addExtState(SND_EXT_INRSRC);
        } else {
            removeExtState(SND_EXT_INRSRC);
        }
    }
    private RenderingScene rsc = null;

    @Override
    public RenderingScene getRenderingScene() {
        return rsc;
    }

    @Override
    public void setRenderingScene(RenderingScene renderingScene) {
        rsc = renderingScene;
    }

    /**
     * dis/enables OpenAL (kills/creates the AL context if needed)
     *
     * @param openALEnabled
     */
    public static void _setOpenALEnabled(boolean openALEnabled) {
        SoundInput.openALEnabled = openALEnabled;
        if (!openALEnabled) {
            _killAL();
        } else {
            _loadAL();
        }
    }

    /**
     * returns true or false, whether OpenAL is enabled or not, resp.
     *
     * @return
     */
    public static boolean _isOpenALEnabled() {
        return openALEnabled;
    }

    /**
     * enables OpenAL output (.mp3 is not supported with OpenAL) if
     * {@linkplain #_isOpenALEnabled()} returns false, this method does nothing
     *
     * @param b
     */
    @Override
    public void setHardwareAccel(boolean b) {
        if (openALEnabled) {
            switchState(SND_INTERFACE_BIT, b ? SND_INTERFACE_OPENAL : isUseJLayerEnabled() ? SND_INTERFACE_JLAYER : SND_INTERFACE_APPLET);
            if (b) {
                _loadAL();
            }
        } else {
            if (JXAenvUtils._debug) {
                System.err.println(JXAenvUtils.log("OpenAL is not enabled so hardware acceleration of sfx is not available. To enable : SoundInput.setOpenALEnabled(true)", JXAenvUtils.LVL.APP_WRN));
            }
        }
    }

    /**
     * returns true or false, whether OpenAL output is enabled or disabled ,
     * resp.
     *
     * @return
     */
    @Override
    public boolean isHardwareAccel() {
        return (soundState & bits._getMask(SND_INTERFACE_BIT) & SND_INTERFACE_OPENAL) != 0;
    }
}
TOP

Related Classes of net.sf.jiga.xtended.impl.SoundInput

TOP
Copyright © 2018 www.massapi.com. All rights reserved.
All source code are property of their respective owners. Java is a trademark of Sun Microsystems, Inc and owned by ORACLE Inc. Contact coftware#gmail.com.