2016-03-03 132 views
0

我在播放样本Allegro 5时遇到了问题。当我播放样本时,我无法再播放该样本,直到它完成播放。如果另一个不同的样本正在播放,有时它也不会播放样本。Allegro 5一次播放多个样本

无论如何解决这个问题?

我用一个只有播放功能的“声音”类播放音频。其余的是构造函数和成员变量,所有这些都用于播放函数中。

void Sound::play() 
{ 
    al_play_sample(
     pSample, // ALLEGRO_SAMPLE 
     mGain,  // float 
     mPan,  // float 
     mSpeed,  // float 
     getPlaymode(mPlaymode), // I use my own non-AL playmode enums. This is a private function that returns the AL version. 
     NULL);  // ALLEGRO_SAMPLE_ID 
} 

全班:

Sound.h

class ContentManager; 

enum Playmode 
{ 
    BiDir, 
    Loop, 
    Once, 
    StreamOnce, 
    StreamOneDir 
}; 

class Sound : public Trackable 
{ 
private: 
    /* Variables 
    * * * * * * * * * * * * */ 
    ALLEGRO_SAMPLE* pSample; 

    float 
     mGain, 
     mPan, 
     mSpeed; 

    Playmode mPlaymode; 

    std::string 
     mAssetPath, 
     mAssetName; 

    /* Private Functions 
    * * * * * * * * * * * * */ 
    ALLEGRO_PLAYMODE getPlaymode(Playmode playmode) 
    { 
     switch (playmode) 
     { 
      case BiDir: 
       return ALLEGRO_PLAYMODE::ALLEGRO_PLAYMODE_BIDIR; 

      case Loop: 
       return ALLEGRO_PLAYMODE::ALLEGRO_PLAYMODE_LOOP; 

      case Once: 
       return ALLEGRO_PLAYMODE::ALLEGRO_PLAYMODE_ONCE; 

      case StreamOnce: 
       return ALLEGRO_PLAYMODE::_ALLEGRO_PLAYMODE_STREAM_ONCE; 

      case StreamOneDir: 
       return ALLEGRO_PLAYMODE::_ALLEGRO_PLAYMODE_STREAM_ONEDIR; 

      // Default to once 
      default: 
       return ALLEGRO_PLAYMODE::ALLEGRO_PLAYMODE_ONCE; 
     } 
    } 

public: 
    /* Constructors/Destructor 
    * * * * * * * * * * * * */ 
    Sound(); 

    Sound(
     // assetPath, assetName, gain, pan, speed, playmode 
     std::string assetPath, 
     std::string assetName, 
     float gain = 1.0f, 
     float pan = 0.0f, 
     float speed = 1.0f, 
     Playmode playmode = Once); 

    Sound(const Sound& other); 

    ~Sound(); 

    friend class ContentManager; // My content system. 

    void play(); 

}; 

Sound.cpp

#include "Sound.h" 

/* Constructors/Destructor 
* * * * * * * * * * * * */ 
Sound::Sound() 
{ 
    this->mAssetPath = ""; 
    this->mAssetName = ""; 
    this->mGain = 1.0f; 
    this->mPan = 0.0f; 
    this->mSpeed = 1.0f; 
    this->mPlaymode = Once; 

    this->pSample = NULL; 
} 

Sound::Sound(std::string assetPath, std::string assetName, float gain, float pan, float speed, Playmode playmode) 
{ 
    this->mAssetPath = assetPath; 
    this->mAssetName = assetName; 
    this->mGain = gain; 
    this->mPan = pan; 
    this->mSpeed = speed; 
    this->mPlaymode = playmode; 

    this->pSample = al_load_sample((assetPath + assetName).c_str()); 
} 

Sound::Sound(const Sound& other) 
{ 
    this->mAssetPath = other.mAssetPath; 
    this->mAssetName = other.mAssetName;  
    this->mGain = other.mGain; 
    this->mPan = other.mPan; 
    this->mSpeed = other.mSpeed; 
    this->mPlaymode = other.mPlaymode; 

    this->pSample = al_load_sample((mAssetPath + mAssetName).c_str()); 
} 

Sound::~Sound() 
{ 
    al_destroy_sample(pSample); 
} 


void Sound::play() 
{ 
    al_play_sample(
     pSample, 
     mGain, 
     mPan, 
     mSpeed, 
     getPlaymode(mPlaymode), 
     NULL); 
} 

我所说的播放功能,通过我的系统的休息,这看起来像这样:

// Game->ContentManager->Sound->play() 
Game::instance()->content()->getSound("somesound.wav")->play(); 

内容管理器包含我的资产的地图。

这是我正在为一个班级工作的较大项目的一部分,但不是,这部分不是作业。我的教授不允许我们拥有任何公共/顶级AL代码(例如,没有公开AL返回等)。

让我知道我是否需要澄清任何事情。任何帮助总是感激。

回答

0

我可能是错的,但它听起来像是你有使用al_reserve_samples(number_of_samples);

+0

我会尝试,当我得到一个机会。谢谢。 – Gurman8r

0

基于关闭ppsz的答案,以预留更多的样本,我做了一些挖掘和下面根据我发现了什么一样。

int numSamples = /*Some int*/ 
int reservedSamples = 0; 
int i = (numSamples >= 1 ? numSamples : 1); 
bool success = false; 

do 
{ 
    success = al_reserve_samples(i); 

    i -= 1; 
} 
while (success == false || i > 0); 

Source