diff options
author | Max Horn | 2005-01-01 19:19:06 +0000 |
---|---|---|
committer | Max Horn | 2005-01-01 19:19:06 +0000 |
commit | 74bf578bda4c9adcc70ce4cda7d4617a9b95267c (patch) | |
tree | b46f1664b5ffd69ebc5623f83444fd7f5de724e2 | |
parent | c418282ec724d01e37b13f7372aa2d6b48f6cbe2 (diff) | |
download | scummvm-rg350-74bf578bda4c9adcc70ce4cda7d4617a9b95267c.tar.gz scummvm-rg350-74bf578bda4c9adcc70ce4cda7d4617a9b95267c.tar.bz2 scummvm-rg350-74bf578bda4c9adcc70ce4cda7d4617a9b95267c.zip |
Changed the singleton code to allow for custom object factories; this allowed me to change OSystem to use the singleton base class, too
svn-id: r16404
-rw-r--r-- | base/plugins.h | 4 | ||||
-rw-r--r-- | common/config-manager.h | 5 | ||||
-rw-r--r-- | common/singleton.h | 20 | ||||
-rw-r--r-- | common/system.cpp | 12 | ||||
-rw-r--r-- | common/system.h | 26 | ||||
-rw-r--r-- | gui/newgui.h | 2 | ||||
-rw-r--r-- | sound/audiocd.h | 2 |
7 files changed, 37 insertions, 34 deletions
diff --git a/base/plugins.h b/base/plugins.h index b1eec1328d..6252bfeaaf 100644 --- a/base/plugins.h +++ b/base/plugins.h @@ -103,6 +103,8 @@ public: typedef Common::Array<Plugin *> PluginList; +class PluginManager; + /** * Instances of this class manage all plugins, including loading them, * making wrapper objects of class Plugin available, and unloading them. @@ -115,7 +117,7 @@ private: bool tryLoadPlugin(Plugin *plugin); - friend class Common::Singleton<PluginManager>; + friend SingletonBaseType *makeInstance<>(); PluginManager(); public: diff --git a/common/config-manager.h b/common/config-manager.h index fd51d6ac37..45d7912b64 100644 --- a/common/config-manager.h +++ b/common/config-manager.h @@ -38,9 +38,6 @@ namespace Common { * @todo Implement the callback based notification system (outline below) * which sends out notifications to interested parties whenever the value * of some specific (or any) configuration key changes. - * @todo Preserve the order of the entries in the config file. Maybe even add - * an API to query/modify that order, which could be used by the launcher - * to allow arranging the game targets. */ class ConfigManager : public Singleton<ConfigManager> { struct IgnoreCaseComparator { @@ -117,7 +114,7 @@ public: */ private: - friend class Singleton<ConfigManager>; + friend SingletonBaseType *makeInstance<>(); ConfigManager(); void loadFile(const String &filename); diff --git a/common/singleton.h b/common/singleton.h index 4b21e929aa..a436d506b8 100644 --- a/common/singleton.h +++ b/common/singleton.h @@ -23,6 +23,18 @@ #ifndef COMMON_SINGLETON_H #define COMMON_SINGLETON_H +/** + * The default object factory used by the template class Singleton. + * By specialising this template function, one can make a singleton use a + * custom object factory. For example, to support encapsulation, your + * singleton class might be pure virtual (or "abstract" in Java terminology), + * and you specialise makeInstance to return an instance of a subclass. + */ +template <class T> +T* makeInstance() { + return new T(); +} + namespace Common { /** @@ -47,13 +59,15 @@ public: // order might become an issue. There are various approaches // to solve that problem, but for now this is sufficient if (!_singleton) - _singleton = new T; + _singleton = makeInstance<T>(); return *_singleton; } protected: Singleton<T>() { } - ~Singleton<T>() { } -}; + virtual ~Singleton<T>() { } + + typedef T SingletonBaseType; +}; #define DECLARE_SINGLETON(T) template<> T* Common::Singleton<T>::_singleton=0 diff --git a/common/system.cpp b/common/system.cpp index 9c465a14fb..db020a2e5f 100644 --- a/common/system.cpp +++ b/common/system.cpp @@ -31,9 +31,10 @@ #include "common/config-manager.h" #include "common/system.h" -static OSystem *s_system = 0; +DECLARE_SINGLETON(OSystem); -static OSystem *createSystem() { +template <> +OSystem *makeInstance<>() { // Attention: Do not call parseGraphicsMode() here, nor any other function // which needs to access the OSystem instance, else you get stuck in an // endless loop. @@ -58,13 +59,6 @@ static OSystem *createSystem() { #endif } -OSystem &OSystem::instance() { - if (!s_system) - s_system = createSystem(); - return *s_system; -} - - bool OSystem::setGraphicsMode(const char *name) { if (!name) return false; diff --git a/common/system.h b/common/system.h index 2a3b0fafc1..617cb5c052 100644 --- a/common/system.h +++ b/common/system.h @@ -27,6 +27,16 @@ #include "common/util.h" #include "common/rect.h" #include "common/savefile.h" +#include "common/singleton.h" + +class OSystem; + +/** + * Custome object factory for OSystem. + */ +template <> +OSystem *makeInstance<>(); + /** * Interface for ScummVM backends. If you want to port ScummVM to a system @@ -38,22 +48,8 @@ * methods to create timers, to handle user input events, * control audio CD playback, and sound output. */ -class OSystem { +class OSystem : public Common::Singleton<OSystem> { public: - /** - * Returns a pointer to the (singleton) OSystem instance, that is, to the - * active backend. - * This is not quite a "proper" singleton, since OSystem is an interface - * not a real class (and thus it isn't based on our Singleton template). - * @return the pointer to the (singleton) OSystem instance - */ - static OSystem &instance(); - -public: - - /** Empty virtual destructor. DO NOT REMOVE! */ - virtual ~OSystem() {} - /** @name Feature flags */ //@{ diff --git a/gui/newgui.h b/gui/newgui.h index 46cf9de657..e8c0eae556 100644 --- a/gui/newgui.h +++ b/gui/newgui.h @@ -56,7 +56,7 @@ typedef Common::FixedStack<Dialog *> DialogStack; class NewGui : public Common::Singleton<NewGui> { typedef Common::String String; friend class Dialog; - friend class Common::Singleton<NewGui>; + friend SingletonBaseType *makeInstance<>(); NewGui(); public: diff --git a/sound/audiocd.h b/sound/audiocd.h index 98ab462d9a..e852b2939f 100644 --- a/sound/audiocd.h +++ b/sound/audiocd.h @@ -54,7 +54,7 @@ public: Status getStatus() const; private: - friend class Common::Singleton<AudioCDManager>; + friend SingletonBaseType *makeInstance<>(); AudioCDManager(); int getCachedTrack(int track); |