Added new FileLibrary class to handle music, this fixes a number of issues.

actorid
Michael Papageorgiou 13 years ago
parent 54353794e5
commit 054a176c86

@ -118,8 +118,7 @@ bool OMW::Engine::frameRenderingQueued (const Ogre::FrameEvent& evt)
// sound
if (mUseSound)
{
if (!mEnvironment.mSoundManager->isMusicPlaying())
mEnvironment.mSoundManager->startRandomTitle();
mEnvironment.mSoundManager->playPlaylist();
mEnvironment.mSoundManager->update (evt.timeSinceLastFrame);
}
@ -389,7 +388,7 @@ void OMW::Engine::go()
mOgre->getRoot()->addFrameListener (this);
// Play some good 'ol tunes
mEnvironment.mSoundManager->startRandomTitle();
mEnvironment.mSoundManager->playPlaylist(std::string("Explore"));
// scripts
if (mCompileAll)

@ -13,7 +13,6 @@
#include <components/file_finder/file_finder.hpp>
#include <components/esm_store/store.hpp>
#include "../mwworld/environment.hpp"
#include "../mwworld/world.hpp"
#include "../mwworld/player.hpp"
@ -45,7 +44,6 @@
using namespace Mangle::Sound;
typedef OEngine::Sound::SoundManager OEManager;
////typedef OEngine::Sound::SoundManagerPtr OEManagerPtr;
// Set the position on a sound based on a Ptr.
static void setPos(SoundPtr &snd, const MWWorld::Ptr ref)
@ -69,11 +67,21 @@ namespace MWSound
, mgr(new OEManager(SoundFactoryPtr(new SOUND_FACTORY)))
, updater(mgr)
, cameraTracker(mgr)
, mCurrentPlaylist(NULL)
{
if(useSound)
{
// Make a list of all the sounds
// Temporary list of all sound directories
Files::PathContainer soundDirs;
// The music library will accept these filetypes
// If none is given then it will accept all filetypes
std::vector<std::string> acceptableExtensions;
acceptableExtensions.push_back(".mp3");
acceptableExtensions.push_back(".wav");
acceptableExtensions.push_back(".ogg");
acceptableExtensions.push_back(".flac");
for (Files::PathContainer::const_iterator it = dataDirs.begin(); it != dataDirs.end(); ++it)
{
soundDirs.push_back( *it / std::string("Sound"));
@ -83,17 +91,14 @@ namespace MWSound
Files::FileLister(*it, mSoundFiles, true);
}
// Make a list of all the music tracks
Files::PathContainer musicDirs;
for (Files::PathContainer::const_iterator it = dataDirs.begin(); it != dataDirs.end(); ++it)
{
musicDirs.push_back( *it / std::string("Music") / std::string("Explore"));
}
for (Files::PathContainer::const_iterator it = musicDirs.begin(); it != musicDirs.end(); ++it)
{
Files::FileLister(*it, mMusicFiles, true);
mMusicLibrary.add(*it / std::string("Music"), true, mFSStrict, acceptableExtensions);
}
std::string anything = "anything"; // anything is better that a segfault
mCurrentPlaylist = mMusicLibrary.section(anything, mFSStrict); // now points to an empty path
std::cout << "Sound output: " << SOUND_OUT << std::endl;
std::cout << "Sound decoder: " << SOUND_IN << std::endl;
// Attach the camera to the camera tracker
@ -287,7 +292,8 @@ namespace MWSound
void SoundManager::streamMusic(const std::string& filename)
{
std::string filePath = Files::FileListLocator(mMusicFiles, filename, mFSStrict);
std::cout << filename << std::endl;
std::string filePath = mMusicLibrary.locate(filename, mFSStrict).string();
if(!filePath.empty())
{
streamMusicFull(filePath);
@ -296,11 +302,11 @@ namespace MWSound
void SoundManager::startRandomTitle()
{
if(!mMusicFiles.empty())
if(mCurrentPlaylist && !mCurrentPlaylist->empty())
{
Files::PathContainer::iterator fileIter = mMusicFiles.begin();
Files::PathContainer::const_iterator fileIter = mCurrentPlaylist->begin();
srand( time(NULL) );
int r = rand() % mMusicFiles.size() + 1; //old random code
int r = rand() % mCurrentPlaylist->size() + 1; //old random code
std::advance(fileIter, r - 1);
std::string music = fileIter->string();
@ -327,6 +333,42 @@ namespace MWSound
return test;
}
bool SoundManager::setPlaylist(std::string playlist)
{
const Files::PathContainer* previousPlaylist;
previousPlaylist = mCurrentPlaylist;
if(mMusicLibrary.containsSection(playlist, mFSStrict))
{
mCurrentPlaylist = mMusicLibrary.section(playlist, mFSStrict);
}
else
{
std::cout << "Warning: playlist named " << playlist << " does not exist.\n";
}
return previousPlaylist == mCurrentPlaylist;
}
void SoundManager::playPlaylist(std::string playlist)
{
if (playlist == "")
{
if(!isMusicPlaying())
{
startRandomTitle();
}
return;
}
if(!setPlaylist(playlist))
{
startRandomTitle();
}
else if (!isMusicPlaying())
{
startRandomTitle();
}
}
void SoundManager::say (MWWorld::Ptr ptr, const std::string& filename)
{
// The range values are not tested

@ -12,6 +12,7 @@
#include <openengine/sound/sndmanager.hpp>
#include <components/files/fileops.hpp>
#include <components/file_finder/file_finder.hpp>
#include <components/files/filelibrary.hpp>
#include "../mwworld/ptr.hpp"
@ -86,7 +87,9 @@ namespace MWSound
Files::PathContainer mSoundFiles;
Files::PathContainer mMusicFiles;
Files::FileLibrary mMusicLibrary;
const Files::PathContainer* mCurrentPlaylist;
std::string lookup(const std::string &soundId,
float &volume, float &min, float &max);
@ -115,6 +118,17 @@ namespace MWSound
bool isMusicPlaying();
bool setPlaylist(std::string playlist="");
///< Set the playlist to an existing folder
/// \param name of the folder that contains the playlist
/// if none is set then it is set to an empty playlist
/// \return Return true if the previous playlist was the same
void playPlaylist(std::string playlist="");
///< Start playing music from the selected folder
/// \param name of the folder that contains the playlist
/// if none is set then it plays from the current playlist
void say (MWWorld::Ptr reference, const std::string& filename);
///< Make an actor say some text.
/// \param filename name of a sound file in "Sound/Vo/" in the data directory.

@ -44,6 +44,7 @@ add_component_dir (misc
add_component_dir (files
linuxpath windowspath macospath fixedpath multidircollection collections fileops configurationmanager
filelibrary
)
add_component_dir (compiler

@ -0,0 +1,113 @@
#include "filelibrary.hpp"
#include <iostream>
#include <boost/algorithm/string.hpp>
namespace Files
{
// Looks for a string in a vector of strings
bool containsVectorString(const StringVector& list, const std::string& str)
{
for (StringVector::const_iterator iter = list.begin();
iter != list.end(); iter++)
{
if (*iter == str)
return true;
}
return false;
}
// Searches a path and adds the results to the library
void FileLibrary::add(const boost::filesystem::path &root, bool recursive, bool strict,
const StringVector &acceptableExtensions)
{
PathContainer list;
std::string fileExtension;
std::string type;
FileLister(root, list, recursive);
for (PathContainer::iterator listIter = list.begin();
listIter != list.end(); ++listIter)
{
if( !acceptableExtensions.empty() )
{
fileExtension = listIter->extension().string();
boost::algorithm::to_lower(fileExtension);
if(!containsVectorString(acceptableExtensions, fileExtension))
continue;
}
type = listIter->parent_path().leaf().string();
if (!strict)
boost::algorithm::to_lower(type);
mMap[type].push_back(*listIter);
//std::cout << "Added path: " << listIter->string() << " in section "<< type <<std::endl;
}
}
// Returns true if the named section exists
bool FileLibrary::containsSection(std::string sectionName, bool strict)
{
if (!strict)
boost::algorithm::to_lower(sectionName);
StringPathContMap::const_iterator mapIter = mMap.find(sectionName);
if (mapIter == mMap.end())
return false;
else
return true;
}
// Returns a pointer to const for a section of the library
const PathContainer* FileLibrary::section(std::string sectionName, bool strict)
{
if (!strict)
boost::algorithm::to_lower(sectionName);
StringPathContMap::const_iterator mapIter = mMap.find(sectionName);
if (mapIter == mMap.end())
{
//std::cout << "Empty\n";
return &mEmptyPath;
}
else
{
return &(mapIter->second);
}
}
// Searches the library for an item and returns a boost path to it
boost::filesystem::path FileLibrary::locate(std::string item, bool strict, std::string sectionName)
{
boost::filesystem::path result("");
if (sectionName == "")
{
for(StringPathContMap::iterator iter = mMap.begin(); iter != mMap.end(); iter++)
{
result = FileListLocator(iter->second, boost::filesystem::path(item), strict);
if (result != boost::filesystem::path(""))
return result;
}
}
else
{
if (!containsSection(sectionName, strict))
{
std::cout << "Warning: There is no section named " << sectionName << "\n";
return result;
}
result = FileListLocator(mMap[sectionName], boost::filesystem::path(item), strict);
}
return result;
}
// Prints all the available sections, used for debugging
void FileLibrary::printSections()
{
for(StringPathContMap::const_iterator mapIter = mMap.begin();
mapIter != mMap.end(); mapIter++)
{
std::cout << mapIter->first <<std::endl;
}
}
}

@ -0,0 +1,48 @@
#ifndef COMPONENTS_FILES_FILELIBRARY_HPP
#define COMPONENTS_FILES_FILELIBRARY_HPP
#include <components/files/fileops.hpp>
namespace Files
{
typedef std::map<std::string, PathContainer> StringPathContMap;
typedef std::vector<std::string> StringVector;
/// Looks for a string in a vector of strings
bool containsVectorString(const StringVector& list, const std::string& str);
/// \brief Searches directories and makes lists of files according to folder name
class FileLibrary
{
private:
StringPathContMap mMap;
PathContainer mEmptyPath;
public:
/// Searches a path and adds the results to the library
/// Recursive search and fs strict options are available
/// Takes a vector of acceptable files extensions, if none is given it lists everything.
void add(const boost::filesystem::path &root, bool recursive, bool strict,
const StringVector &acceptableExtensions);
/// Returns true if the named section exists
/// You can run this check before running section()
bool containsSection(std::string sectionName, bool strict);
/// Returns a pointer to const for a section of the library
/// which is essentially a PathContainer.
/// If the section does not exists it returns a pointer to an empty path.
const PathContainer* section(std::string sectionName, bool strict);
/// Searches the library for an item and returns a boost path to it
/// Optionally you can provide a specific section
/// The result is the first that comes up according to alphabetical
/// section naming
boost::filesystem::path locate(std::string item, bool strict, std::string sectionName="");
/// Prints all the available sections, used for debugging
void printSections();
};
}
#endif
Loading…
Cancel
Save