我从本教程中复制/粘贴了OpenAL声音加载器的代码:http://wiki.lwjgl.org/wiki/OpenAL_Tutorial_6_-_Advanced_Loading_and_Error_Handles
但是,每当我尝试加载多个声音时,getALBuffer方法中的for循环就会陷入无限循环。我不认为我改变了我复制/粘贴的任何代码。调用i.next(),其中我是类型Iterator似乎总是返回true,但我不知道为什么。我会发布我的所有复制/粘贴代码,以防我在没有意识到的情况下意外更改某些内容。代码从loadALData()调用开始。
public static String getALErrorString(int err) {
switch (err) {
case AL_NO_ERROR:
return "AL_NO_ERROR";
case AL_INVALID_NAME:
return "AL_INVALID_NAME";
case AL_INVALID_ENUM:
return "AL_INVALID_ENUM";
case AL_INVALID_VALUE:
return "AL_INVALID_VALUE";
case AL_INVALID_OPERATION:
return "AL_INVALID_OPERATION";
case AL_OUT_OF_MEMORY:
return "AL_OUT_OF_MEMORY";
default:
return "No such error code";
}
}
public static String getALCErrorString(int err) {
switch (err) {
case ALC_NO_ERROR:
return "AL_NO_ERROR";
case ALC_INVALID_DEVICE:
return "ALC_INVALID_DEVICE";
case ALC_INVALID_CONTEXT:
return "ALC_INVALID_CONTEXT";
case ALC_INVALID_ENUM:
return "ALC_INVALID_ENUM";
case ALC_INVALID_VALUE:
return "ALC_INVALID_VALUE";
case ALC_OUT_OF_MEMORY:
return "ALC_OUT_OF_MEMORY";
default:
return "no such error code";
}
}
public static int loadALBuffer(String path){
int result;
IntBuffer buffer = BufferUtils.createIntBuffer(1);
// Load wav data into a buffers.
alGenBuffers(buffer);
if ((result = alGetError()) != AL_NO_ERROR){
throw new OpenALException(getALErrorString(result));
}
WaveData waveFile = LoadSound(path);
if (waveFile != null){
alBufferData(buffer.get(0), waveFile.format, waveFile.data, waveFile.samplerate);
waveFile.dispose();
}else{
throw new RuntimeException("No such file: " + path);
}
// Do another error check and return.
if ((result = alGetError()) != AL_NO_ERROR) {
throw new OpenALException(getALErrorString(result));
}
return buffer.get(0);
}
/**
* 1) Checks if file has already been loaded.
* 2) If it has been loaded already, return the buffer id.
* 3) If it has not been loaded, load it and return buffer id.
*/
@SuppressWarnings({ "unchecked", "rawtypes" })
public static int getLoadedALBuffer(String path) {
int count = 0;
for (Iterator i = loadedFiles.iterator(); i.hasNext(); count++) {
if (i.equals(path)) {
return ((Integer) buffers.get(count)).intValue();
}
//I added this if statement to catch the infinite loop
if (count>=100000){
System.out.println("getLoadedALBuffer was caught in an infinite loop!");
return -1;
}
}
int buffer = loadALBuffer(path);
buffers.add(new Integer(buffer));
loadedFiles.add(path);
return buffer;
}
/**
* 1) Creates a source.
* 2) Calls 'GetLoadedALBuffer' with 'path' and uses the returned buffer id as it's sources buffer.
* 3) Returns the source id.
*/
@SuppressWarnings("unchecked")
public static int loadALSample(String path, boolean loop) {
IntBuffer source = BufferUtils.createIntBuffer(1);
int buffer;
int result;
// Get the files buffer id (load it if necessary).
buffer = getLoadedALBuffer(path);
//I added this to handle infinite loop error
if (buffer == -1){
return -1;
}
// Generate a source.
alGenSources(source);
if ((result = alGetError()) != AL_NO_ERROR)
throw new OpenALException(getALErrorString(result));
// Setup the source properties.
alSourcei(source.get(0), AL_BUFFER, buffer);
alSourcef(source.get(0), AL_PITCH, 1.0f);
alSourcef(source.get(0), AL_GAIN, 1.0f);
//alSource(source.get(0), AL_POSITION, sourcePos);
//alSource(source.get(0), AL_VELOCITY, sourceVel);
alSourcei(source.get(0), AL_LOOPING, (loop ? AL_TRUE : AL_FALSE));
// Save the source id.
sources.add(new Integer(source.get(0)));
// Return the source id.
return source.get(0);
}
//I created this method
public static int LoadWaveFile(String name, int location, boolean loop){
return loadALSample(getWaveFilePath(name,location), loop);
}
/**
* 1) Releases temporary loading phase data.
*/
public static void killALLoadedData() {
loadedFiles.clear();
}
// Source id's.
public static int busterShot;
public static int lifeGain;
public static void loadALData() {
// Anything for your application here. No worrying about buffers.
busterShot = LoadWaveFile("MM_Shoot", SFX_FOLDER, false);
lifeGain = LoadWaveFile("MM_1up", SFX_FOLDER, false);
killALLoadedData();
}
//I created these integers
public static final int MUSIC_FOLDER = 0;
public static final int SFX_FOLDER = 1;
//I created this method
public static WaveData LoadSound(String path){
System.out.println("\nLoadSound() called!");
WaveData sound = null;
try {
sound = WaveData.create(new BufferedInputStream(new FileInputStream(path)));
System.out.println(path+((sound!=null) ? " exists!" : " does not exist!"));
} catch (Exception e) {
e.printStackTrace();
}
return sound;
}
//I created this method
public static WaveData QuickLoad(String name, int location){
WaveData sound = LoadSound(getWaveFilePath(name, location));
return sound;
}
//I created this Method
public static String getWaveFilePath(String name, int location){
if (location == MUSIC_FOLDER){
return "res/sounds/music/"+name+".wav";
}else if(location == SFX_FOLDER){
return "res/sounds/soundEffects/"+name+".wav";
}
return null;
}
编辑:当我运行此代码时,这是我的控制台输出:
LoadSound()调用!
res / sounds / soundEffects / MM_Shoot.wav存在!
getLoadedALBuffer陷入无限循环!
答案 0 :(得分:2)
增加迭代器:
for(Iterator i = ... ; i.hasNext(); i.next())
答案 1 :(得分:0)
解决方案是,即使Iterator的元素数量随着添加的wave数据文件的增加而增加,for循环也不会增加到Iterator的不同元素。
这是官方lwjgl网站自带教程的编程问题!我没想到,因此我的困惑。老实说虽然我应该早点看到这个错误。我很抱歉这个愚蠢的问题!