OSDN Git Service

Moved all the Sound-specific functions into MUtilities library.
authorLoRd_MuldeR <mulder2@gmx.de>
Fri, 5 Dec 2014 20:07:06 +0000 (21:07 +0100)
committerLoRd_MuldeR <mulder2@gmx.de>
Fri, 5 Dec 2014 20:07:06 +0000 (21:07 +0100)
MUtilities_VS2013.vcxproj
MUtilities_VS2013.vcxproj.filters
include/MUtils/Global.h
include/MUtils/Sound.h [new file with mode: 0644]
src/Global.cpp
src/Sound_Win32.cpp [new file with mode: 0644]

index 4c86384..16a7da4 100644 (file)
@@ -25,6 +25,7 @@
     <ClCompile Include="src\GUI.cpp" />
     <ClCompile Include="src\KeccakHash.cpp" />
     <ClCompile Include="src\OSSupport_Win32.cpp" />
+    <ClCompile Include="src\Sound_Win32.cpp" />
     <ClCompile Include="src\Startup.cpp" />
     <ClCompile Include="src\Terminal_Win32.cpp" />
     <ClCompile Include="src\UpdateChecker.cpp" />
@@ -38,6 +39,7 @@
     <ClInclude Include="include\MUtils\GUI.h" />
     <ClInclude Include="include\MUtils\KeccakHash.h" />
     <ClInclude Include="include\MUtils\OSSupport.h" />
+    <ClInclude Include="include\MUtils\Sound.h" />
     <ClInclude Include="include\MUtils\Startup.h" />
     <ClInclude Include="include\MUtils\Terminal.h" />
     <ClInclude Include="src\3rd_party\keccak\include\keccak_impl.h" />
       <SubSystem>Windows</SubSystem>
       <GenerateDebugInformation>true</GenerateDebugInformation>
       <AdditionalLibraryDirectories>$(QTDIR)\lib;$(SolutionDir)\..\Prerequisites\VisualLeakDetector\lib\Win32</AdditionalLibraryDirectories>
-      <AdditionalDependencies>QtCored4.lib;QtGuid4.lib;Psapi.lib;Sensapi.lib;PowrProf.lib;%(AdditionalDependencies)</AdditionalDependencies>
+      <AdditionalDependencies>QtCored4.lib;QtGuid4.lib;Winmm.lib;Psapi.lib;Sensapi.lib;PowrProf.lib;%(AdditionalDependencies)</AdditionalDependencies>
     </Link>
   </ItemDefinitionGroup>
   <ItemDefinitionGroup Condition="'$(Configuration)|$(Platform)'=='Release|Win32'">
       <EnableCOMDATFolding>true</EnableCOMDATFolding>
       <OptimizeReferences>true</OptimizeReferences>
       <AdditionalLibraryDirectories>$(QTDIR)\lib;$(SolutionDir)\..\Prerequisites\VisualLeakDetector\lib\Win32</AdditionalLibraryDirectories>
-      <AdditionalDependencies>QtCore4.lib;QtGui4.lib;Psapi.lib;Sensapi.lib;PowrProf.lib;%(AdditionalDependencies)</AdditionalDependencies>
+      <AdditionalDependencies>QtCore4.lib;QtGui4.lib;Winmm.lib;Psapi.lib;Sensapi.lib;PowrProf.lib;%(AdditionalDependencies)</AdditionalDependencies>
       <GenerateDebugInformation>false</GenerateDebugInformation>
     </Link>
   </ItemDefinitionGroup>
index 17a0908..d4318a0 100644 (file)
@@ -69,6 +69,9 @@
     <ClCompile Include="$(SolutionDir)\tmp\$(ProjectName)\MOC_UpdateChecker.cpp">
       <Filter>Source Files\Generated</Filter>
     </ClCompile>
+    <ClCompile Include="src\Sound_Win32.cpp">
+      <Filter>Source Files</Filter>
+    </ClCompile>
   </ItemGroup>
   <ItemGroup>
     <ClInclude Include="src\CriticalSection_Win32.h">
     <ClInclude Include="src\3rd_party\keccak\include\keccak_impl.h">
       <Filter>Header Files\3rd Party</Filter>
     </ClInclude>
+    <ClInclude Include="include\MUtils\Sound.h">
+      <Filter>Public Headers</Filter>
+    </ClInclude>
   </ItemGroup>
   <ItemGroup>
     <CustomBuild Include="include\Mutils\UpdateChecker.h">
index 16029ca..07750a7 100644 (file)
@@ -91,6 +91,10 @@ namespace MUtils
        //String sorting
        MUTILS_API void natural_string_sort(QStringList &list, const bool bIgnoreCase);
 
+       //Clean file path
+       MUTILS_API QString clean_file_name(const QString &name);
+       MUTILS_API QString clean_file_path(const QString &path);
+
        //Internal
        namespace Internal
        {
diff --git a/include/MUtils/Sound.h b/include/MUtils/Sound.h
new file mode 100644 (file)
index 0000000..7895d11
--- /dev/null
@@ -0,0 +1,54 @@
+///////////////////////////////////////////////////////////////////////////////
+// MuldeR's Utilities for Qt
+// Copyright (C) 2004-2014 LoRd_MuldeR <MuldeR2@GMX.de>
+//
+// This library is free software; you can redistribute it and/or
+// modify it under the terms of the GNU Lesser General Public
+// License as published by the Free Software Foundation; either
+// version 2.1 of the License, or (at your option) any later version.
+//
+// This library is distributed in the hope that it will be useful,
+// but WITHOUT ANY WARRANTY; without even the implied warranty of
+// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
+// Lesser General Public License for more details.
+//
+// You should have received a copy of the GNU Lesser General Public
+// License along with this library; if not, write to the Free Software
+// Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA  02110-1301  USA
+//
+// http://www.gnu.org/licenses/lgpl-2.1.txt
+//////////////////////////////////////////////////////////////////////////////////
+
+#pragma once
+
+//MUtils
+#include <MUtils/Global.h>
+
+///////////////////////////////////////////////////////////////////////////////
+
+namespace MUtils
+{
+       namespace Sound
+       {
+               enum beep_t
+               {
+                       BEEP_NFO = 0,
+                       BEEP_WRN = 1,
+                       BEEP_ERR = 2
+               };
+
+               //Simple beep
+               MUTILS_API bool beep(beep_t beepType);
+
+               //Play built-in sound by name
+               MUTILS_API bool play_sound(const QString &name, const bool bAsync);
+
+               //Play system sound by name
+               MUTILS_API bool play_system_sound(const QString &alias, const bool bAsync);
+
+               //Play sound from file
+               MUTILS_API bool play_sound_file(const QString &library, const unsigned short uiSoundIdx);
+       }
+}
+
+///////////////////////////////////////////////////////////////////////////////
index 7206d77..984b56d 100644 (file)
@@ -327,6 +327,58 @@ void MUtils::natural_string_sort(QStringList &list, const bool bIgnoreCase)
 }
 
 ///////////////////////////////////////////////////////////////////////////////
+// CLEAN FILE PATH
+///////////////////////////////////////////////////////////////////////////////
+
+static const struct
+{
+       const char *const search;
+       const char *const replace;
+}
+CLEAN_FILE_NAME[] =
+{
+       { "\\",  "-"  },
+       { " / ", ", " },
+       { "/",   ","  },
+       { ":",   "-"  },
+       { "*",   "x"  },
+       { "?",   "!"  },
+       { "<",   "["  },
+       { ">",   "]"  },
+       { "|",   "!"  },
+       { "\"",  "'"  },
+       { NULL,  NULL }
+};
+
+QString MUtils::clean_file_name(const QString &name)
+{
+       QString str = name.simplified();
+
+       for(size_t i = 0; CLEAN_FILE_NAME[i].search; i++) 
+       {
+               str.replace(CLEAN_FILE_NAME[i].search, CLEAN_FILE_NAME[i].replace);
+       }
+       
+       QRegExp regExp("\"(.+)\"");
+       regExp.setMinimal(true);
+       str.replace(regExp, "`\\1ยด");
+       
+       return str.simplified();
+}
+
+QString MUtils::clean_file_path(const QString &path)
+{
+       QStringList parts = path.simplified().replace("\\", "/").split("/", QString::SkipEmptyParts);
+
+       for(int i = 0; i < parts.count(); i++)
+       {
+               parts[i] = MUtils::clean_file_name(parts[i]);
+       }
+
+       return parts.join("/");
+}
+
+///////////////////////////////////////////////////////////////////////////////
 // SELF-TEST
 ///////////////////////////////////////////////////////////////////////////////
 
diff --git a/src/Sound_Win32.cpp b/src/Sound_Win32.cpp
new file mode 100644 (file)
index 0000000..ba6b798
--- /dev/null
@@ -0,0 +1,148 @@
+///////////////////////////////////////////////////////////////////////////////
+// MuldeR's Utilities for Qt
+// Copyright (C) 2004-2014 LoRd_MuldeR <MuldeR2@GMX.de>
+//
+// This library is free software; you can redistribute it and/or
+// modify it under the terms of the GNU Lesser General Public
+// License as published by the Free Software Foundation; either
+// version 2.1 of the License, or (at your option) any later version.
+//
+// This library is distributed in the hope that it will be useful,
+// but WITHOUT ANY WARRANTY; without even the implied warranty of
+// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
+// Lesser General Public License for more details.
+//
+// You should have received a copy of the GNU Lesser General Public
+// License along with this library; if not, write to the Free Software
+// Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA  02110-1301  USA
+//
+// http://www.gnu.org/licenses/lgpl-2.1.txt
+//////////////////////////////////////////////////////////////////////////////////
+
+//Win32 API
+#define WIN32_LEAN_AND_MEAN 1
+#include <Windows.h>
+#include <MMSystem.h>
+
+//MUtils
+#include <MUtils/Sound.h>
+#include <MUtils/OSSupport.h>
+
+//Qt
+#include <QReadWriteLock>
+#include <QHash>
+#include <QResource>
+#include <QFileInfo>
+#include <QDir>
+
+///////////////////////////////////////////////////////////////////////////////
+// BEEP
+///////////////////////////////////////////////////////////////////////////////
+
+bool MUtils::Sound::beep(MUtils::Sound::beep_t beepType)
+{
+       switch(beepType)
+       {
+               case BEEP_NFO: return MessageBeep(MB_ICONASTERISK)    == TRUE; break;
+               case BEEP_WRN: return MessageBeep(MB_ICONEXCLAMATION) == TRUE; break;
+               case BEEP_ERR: return MessageBeep(MB_ICONHAND)        == TRUE; break;
+               default: return false;
+       }
+}
+
+///////////////////////////////////////////////////////////////////////////////
+// PLAY SOUND
+///////////////////////////////////////////////////////////////////////////////
+
+typedef QHash<const QString, const unsigned char*> SoundDB;
+
+static QReadWriteLock g_sound_lock;
+static QScopedPointer<SoundDB> g_sound_db;
+
+static const unsigned char *get_sound_from_cache(const QString &name)
+{
+       //Try to look-up the sound in the cache first
+       QReadLocker readLock(&g_sound_lock);
+       if((!g_sound_db.isNull()) && g_sound_db->contains(name))
+       {
+               return g_sound_db->value(name);
+       }
+
+       //Get the write lock now
+       readLock.unlock();
+       QWriteLocker writeLock(&g_sound_lock);
+
+       //Is sound still not in cache?
+       if((!g_sound_db.isNull()) && g_sound_db->contains(name))
+       {
+               return g_sound_db->value(name);
+       }
+
+       //If data not found in cache, try to load from resource!
+       QResource resource(QString(":/sounds/%1.wav").arg(name));
+       if(resource.isValid())
+       {
+               if(const unsigned char *data = resource.data())
+               {
+                       if(g_sound_db.isNull())
+                       {
+                               g_sound_db.reset(new SoundDB());
+                       }
+                       g_sound_db->insert(name, data);
+                       return data;
+               }
+       }
+
+       qWarning("Sound effect \"%s\" not found!", MUTILS_UTF8(name));
+       return NULL;
+}
+
+bool MUtils::Sound::play_sound(const QString &name, const bool bAsync)
+{
+       if(!name.isEmpty())
+       {
+               if(const unsigned char *data = get_sound_from_cache(name))
+               {
+                       return PlaySound(LPCWSTR(data), NULL, (SND_MEMORY | (bAsync ? SND_ASYNC : SND_SYNC))) != FALSE;
+               }
+       }
+       
+       return false;
+}
+
+bool MUtils::Sound::play_system_sound(const QString &alias, const bool bAsync)
+{
+       return PlaySound(MUTILS_WCHR(alias), GetModuleHandle(NULL), (SND_ALIAS | (bAsync ? SND_ASYNC : SND_SYNC))) != FALSE;
+}
+
+bool MUtils::Sound::play_sound_file(const QString &library, const unsigned short uiSoundIdx)
+{
+       bool result = false;
+
+       QFileInfo libraryFile(library);
+       if(!libraryFile.isAbsolute())
+       {
+               const QString &systemDir = MUtils::OS::known_folder(MUtils::OS::FOLDER_SYSTEMFOLDER);
+               if(!systemDir.isEmpty())
+               {
+                       libraryFile.setFile(QDir(systemDir), libraryFile.fileName());
+               }
+       }
+
+       if(libraryFile.exists() && libraryFile.isFile())
+       {
+               if(const HMODULE module = LoadLibraryW(MUTILS_WCHR(QDir::toNativeSeparators(libraryFile.canonicalFilePath()))))
+               {
+                       result = (PlaySound(MAKEINTRESOURCE(uiSoundIdx), module, (SND_RESOURCE | SND_SYNC)) != FALSE);
+                       FreeLibrary(module);
+               }
+       }
+       else
+       {
+               qWarning("PlaySound: File \"%s\" could not be found!", MUTILS_UTF8(libraryFile.absoluteFilePath()));
+       }
+
+       return result;
+}
+
+///////////////////////////////////////////////////////////////////////////////