Visit the Ultimate Toolbox main page for an overview and configuration guide to the Ultimate Toolbox library.
Source code and project files for this sample can be found in the samples\utility\SoundManager directory of the sample projects download.
Nowadays, more and more computers are equipped with a sound card and sound effects can add another professional feature that distinguish your software. Of course, sound effects are a must for multimedia applications but sometimes it's nice to add some sounds in a regular application too. Wouldn't it be nice to hear some sound when you click over button or play some sound when the mouse moves over some object. Using our new classes it takes only one line of code to associate a sound effect with any object so this effect will be played when specified event is fired.
Note that sounds are usually played in result of some user action (e.g. the mouse left button was clicked or a specific keyboard button was pressed) or in result of some event (e.g. a timer event). Any event which eventually forces an application to play sound we call a sound event. To uniquely identify any such event we define a sound event ID. This approach works well with natural events such as mouse or keyboard events.
In the case when the sound is played due to an application specific event we define it as an application specific message.
Any sound played with in response to a windows message we call a sound message. Now the idea behind the
COXSoundEffectManager class should be clear. Why don't we create the class that will manage sound effects and sound events? It should be only one function to register a sound to be played when a particular event is fired! And as long as sound events are defined as window messages we can come up with the class that will work with any object (static, edit, combobox, button, listbox, tree, list controls etc.).
COXHookWnd class is the parent class of
COXSoundEffectManager. Basically, we hook a window and examine all messages. If the message currently being handling is registered as a sound event message we start to play associated sound using our
COXSoundEffectManager is derived from
COXHookWnd any target window must be attached to
COXSoundEffectManager object using the
After the window is successfully attached you can register whatever sound events are to be played when the corresponding event is fired using
You can use an existing sound file or resource from your application as source of sound and you can set additional options that define the way the sound is played. The sound can be played only once, infinitely or for a fixed number of times. You can also specify whether the sound should be started even though another may be playing.
Some sounds can be pretty lengthy (especially if you used the loop infinitely option). Although any playing sound will be stopped when the hooked window is destroyed or detached using the
Detach function, sometimes it's good idea to define some events that would cause any playing sound to be stopped after being fired. We call such events sound stop events (the sound events that were described before we call sound play events). To register such an event we use the
Of course the same event cannot be registered to play different sounds and cannot be registered as play and stop event simultaneously.
Any stop or play sound events can be unregistered using
To unregister all events simultaneously use
At any time you can test whether a particular event is registered as stop or play sound event using
While programming using
COXSoundEffectManager class to its fullest extent you will find
GetSoundEffect very useful.
You have the option to save, in the registry, all registered play and stop sound events and sound effects. Use
SaveState to save to the registry and
LoadState to retrieve the previously saved state.
If you don't want to save the state of the Sound Effect Manager settings into the registry then you can add the
OXSE_NO_SAVESTATE define to your project and remove the source code for
COXSoundEffectManager has two weaknesses.
First of all, it is designed to handle only with one target window at a time. That means if you want to assign sound effects to five buttons then you have to create five
COXSoundEffectManager objects which adds a lot of weight to your source code. To resolve this problem we created the
COXSoundEffectOrganizer class which can be used to register sound effects for multiple windows. Internally this class creates a
COXSoundEffectManager object for every registered window, but hides this fact from a programmer while providing the same functionality as
COXSoundEffectManager does. Plus
COXSoundEffectOrganizer is aware off all
COXSoundEffectManager objects it manages and can stop or start playing sounds in any of them (that is why the
COXSoundEffectManager constructor is designed to take pointer to a
COXSoundEffectOrganizer object as parameter which must be set to
NULL if the
COXSoundEffectManager object is used as stand-alone).
The samples\utility\SoundManager sample dialog uses a member
COXSoundEffectOrganizer object (include OXSoundEffectManager.h) to add mouse enter and click sounds to static controls on the dialog. (These static controls are subclassed
COXStaticText objects with overrides that enhance the visual effects of the enter and click events).
The dialog implements a member function
SetupStaticControl that is called from
OnInitDialog to initialize color and sound effect events:
void CSoundManagerDlg::SetupStaticControl(CMyStatic* m_pctl, COLORREF clrText,
COLORREF clrBack, int nFontHeight,
int nFontWeight,CString sFontName,
BOOL bEmboss, int nHorzAlignment,
And sets the properties of the
COXStaticHyperLink 'about' control in the
OnInitDialog method. (The heartbeat is quite scary):
"Information about COXSoundEffectOrganizer"));
It is highly recommended to use
COXSoundEffectOrganizer instead of
COXSoundEffectManager even in situations when you provide sound effects only for one window.
Another problem has to do with customizing of sound effects. Although we provide basic functions to save into and load from registry state of any
COXSoundEffectManager object, there is still the issue of providing an easy way for users to customize sound effects. Enter the
COXSoundCustomizeDlg class, which layers a pointer to
COXSoundEffectOrganizer object and provides the user an interface to add, delete, and edit any sound events and effects for all windows registered with given
COXSoundEffectOrganizer object (another reason to use always
COXSoundEffectOrganizer instead of
Initial CodeProject release August 2007.