/******************************************************************************* * Copyright 2011 See AUTHORS file. * * Licensed under the Apache License, Version 2.0 (the "License"); you may not use this file except in compliance with * the License. You may obtain a copy of the License at * * http://www.apache.org/licenses/LICENSE-2.0 * * Unless required by applicable law or agreed to in writing, software distributed under the License is distributed on * an "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. See the License for the * specific language governing permissions and limitations under the License. ******************************************************************************/ package com.badlogic.gdx.backends.openal; import java.nio.ByteBuffer; import java.nio.ByteOrder; import com.badlogic.gdx.audio.Sound; import static org.lwjgl.openal.AL10.*; /** @author Nathan Sweet */ public class OpenALSound implements Sound { private int bufferID = -1; private final OpenALAudio audio; private float duration; public OpenALSound(OpenALAudio audio) { this.audio = audio; } void setup(byte[] pcm, int channels, int sampleRate) { int bytes = pcm.length - (pcm.length % (channels > 1 ? 4 : 2)); int samples = bytes / (2 * channels); duration = samples / (float) sampleRate; ByteBuffer buffer = ByteBuffer.allocateDirect(bytes); buffer.order(ByteOrder.nativeOrder()); buffer.put(pcm, 0, bytes); buffer.flip(); if (bufferID == -1) { bufferID = alGenBuffers(); alBufferData(bufferID, channels > 1 ? AL_FORMAT_STEREO16 : AL_FORMAT_MONO16, buffer.asShortBuffer(), sampleRate); } } public long play() { return play(1); } public long play(float volume) { if (audio.noDevice) return 0; int sourceID = audio.obtainSource(false); if (sourceID == -1) return -1; long soundId = audio.getSoundId(sourceID); alSourcei(sourceID, AL_BUFFER, bufferID); alSourcei(sourceID, AL_LOOPING, AL_FALSE); alSourcef(sourceID, AL_GAIN, volume); alSourcePlay(sourceID); return soundId; } public long loop() { return loop(1); } @Override public long loop(float volume) { if (audio.noDevice) return 0; int sourceID = audio.obtainSource(false); if (sourceID == -1) return -1; long soundId = audio.getSoundId(sourceID); alSourcei(sourceID, AL_BUFFER, bufferID); alSourcei(sourceID, AL_LOOPING, AL_TRUE); alSourcef(sourceID, AL_GAIN, volume); alSourcePlay(sourceID); return soundId; } public void stop() { if (audio.noDevice) return; audio.stopSourcesWithBuffer(bufferID); } public void dispose() { if (audio.noDevice) return; if (bufferID == -1) return; audio.freeBuffer(bufferID); alDeleteBuffers(bufferID); bufferID = -1; } @Override public void stop(long soundId) { if (audio.noDevice) return; audio.stopSound(soundId); } @Override public void setPitch(long soundId, float pitch) { if (audio.noDevice) return; audio.setSoundPitch(soundId, pitch); } @Override public void setVolume(long soundId, float volume) { if (audio.noDevice) return; audio.setSoundGain(soundId, volume); } @Override public void setLooping(long soundId, boolean looping) { if (audio.noDevice) return; audio.setSoundLooping(soundId, looping); } @Override public void setPan(long soundId, float pan, float volume) { if (audio.noDevice) return; audio.setSoundPan(soundId, pan, volume); } @Override public long play(float volume, float pitch, float pan) { long id = play(); setPitch(id, pitch); setPan(id, pan, volume); return id; } @Override public long loop(float volume, float pitch, float pan) { long id = loop(); setPitch(id, pitch); setPan(id, pan, volume); return id; } /** Returns the length of the sound in seconds. */ public float duration() { return duration; } @Override public void setPriority(long soundId, int priority) { // TODO Auto-generated method stub } }