diff options
Diffstat (limited to 'libkdegames/highscore/khighscore.h')
-rw-r--r-- | libkdegames/highscore/khighscore.h | 311 |
1 files changed, 311 insertions, 0 deletions
diff --git a/libkdegames/highscore/khighscore.h b/libkdegames/highscore/khighscore.h new file mode 100644 index 00000000..b1e3d25f --- /dev/null +++ b/libkdegames/highscore/khighscore.h @@ -0,0 +1,311 @@ +/* + This file is part of the KDE games library + Copyright (C) 2001 Andreas Beckermann (b_mann@gmx.de) + Copyright (C) 2003 Nicolas Hadacek <hadacek@kde.org> + + This library is free software; you can redistribute it and/or + modify it under the terms of the GNU Library General Public + License version 2 as published by the Free Software Foundation. + + 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 + Library General Public License for more details. + + You should have received a copy of the GNU Library General Public License + along with this library; see the file COPYING.LIB. If not, write to + the Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor, + Boston, MA 02110-1301, USA. +*/ +/* + $Id$ +*/ +#ifndef __KHIGHSCORE_H__ +#define __KHIGHSCORE_H__ + +#include <qstring.h> +#include <qobject.h> +#include <kdemacros.h> +class KConfig; +class KFileLock; +class KRawConfig; +class KHighscorePrivate; + +/** + * @short Class for managing highscore tables + * + * This is the KDE class for saving and reading highscore tables. It offers the + * possibility for system-wide highscore tables (configure with e.g. + * --enable-highscore-dir=/var/games) and a theoretically unlimited number of + * entries. + * + * You can specify different "keys" for an entry - just like the KConfig + * keys. But it will be prefixed with the number of the entry. For example you + * will probably use something like this to save the name of the player on the + * top of the list (ie the winner): + * \code + * highscore->writeEntry(1, "name", myPlayer->name()); + * \endcode + * Note that it doesn't really matter if you use "0" or "1" as the first entry + * of the list as long as your program always uses the same for the first + * entry. I recommend to use "1", as several convenience methods use this. + * + * You can also specify different groups using setHighscoreGroup. Just + * like the keys mentioned above the groups behave like groups in KConfig + * but are prefixed with "KHighscore_". The default group is just "KHighscore". + * You might use this e.g. to create different highscore tables like + * \code + * table->setHighscoreGroup("Easy"); + * // write the highscores for level "easy" to the table + * writeEasyHighscores(table); + * + * table->setHighscore("Player_1"); + * // write player specific highscores to the table + * writePlayerHighscores(table); + * \endcode + * As you can see above you can also use this to write the highscores of a + * single player, so the "best times" of a player. To write highscores for a + * specific player in a specific level you will have to use a more complex way: + * \code + * QString group = QString("%1_%2").arg(player).arg(level); + * table->setGroup(group); + * writeHighscore(table, player, level); + * \endcode + * + * Also note that you MUST NOT mark the key or the group for translation! I.e. + * don't use i18n() for the keys or groups! Here is the code to read the above + * written entry: + * \code + * QString firstName = highscore->readEntry(0, "name"); + * \endcode + * Easy, what? + * @author Andreas Beckermann <b_mann@gmx.de> + **/ +class KDE_EXPORT KHighscore : public QObject +{ + Q_OBJECT +public: + /** @obsolete + * Constructor. The highscore file is forced to be local to support + * games using the old behaviour. + */ + KHighscore(QObject* parent = 0); + + /** + * Constructor. + * + * @param forceLocal if true, the local highscore file is used even + * when the configuration has been set to use a system-wide file. This + * is convenient for converting highscores from legacy applications. + * @param parent parent widget for this widget + * @since 3.2 + */ + KHighscore(bool forceLocal, QObject *parent); + + /** + * Read the current state of the highscore file. Remember that when + * it's not locked for writing, this file can change at any time. + * (This method is only useful for a system-wide highscore file). + * @since 3.2 + */ + void readCurrentConfig(); + + /** @since 3.2 + * This method open the system-wide highscore file using the effective + * group id of the game executable (which should be "games"). The + * effective group id is completely dropped afterwards. + * + * Note: this method should be called in main() before creating a + * KApplication and doing anything else (KApplication checks that the + * program is not suid/sgid and will exit the program for security + * reason if it is the case). + */ + static void init(const char *appname); + + /** @since 3.2 + * Lock the system-wide highscore file for writing (does nothing and + * return true if the local file is used). + * You should perform writing without GUI interaction to avoid + * blocking and don't forget to unlock the file as soon as possible + * with writeAndUnlock(). + * + * If the config file cannot be locked, + * the method waits for 1 second and, if it failed again, displays + * a message box asking for retry or cancel. + * @param widget used as the parent of the message box. + * + * @return false on error or if the config file is locked by another + * process. In such case, the config stays read-only. + */ + bool lockForWriting(QWidget *widget = 0); + + /** + * Effectively write and unlock the system-wide highscore file + * (@see lockForWriting). + * If using a local highscore file, it will sync the config. + * @since 3.2 + */ + void writeAndUnlock(); + + /** + * @return true if the highscore file is locked or if a local + * file is used. + * @since 3.2 + */ + bool isLocked() const; + + /** + * Destructor. + * If necessary, write and unlock the highscore file. + */ + ~KHighscore(); + + /** + * @param entry The number of the entry / the placing of the player + * @param key A key for this entry. E.g. "name" for the name of the + * player. Nearly the same as the usual keys in KConfig - but they + * are prefixed with the entry number + * @param value The value of this entry + **/ + void writeEntry(int entry, const QString& key, const QString& value); + + /** + * This is an overloaded member function, provided for convenience. + * It differs from the above function only in what argument(s) it accepts. + **/ + void writeEntry(int entry, const QString& key, int value); + + /** + * This is an overloaded member function, provided for convenience. + * It differs from the above function only in what argument(s) it accepts. + * See KConfigBase documentation for allowed QVariant::Type. + **/ + void writeEntry(int entry, const QString& key, const QVariant &value); + + /** + * Reads an entry from the highscore table. + * @param entry The number of the entry / the placing to be read + * @param key The key of the entry. E.g. "name" for the name of the + * player. Nearly the same as the usual keys in KConfig - but they + * are prefixed with the entry number + * @param pDefault This will be used as default value if the key+pair + * entry can't be found. + * @return The value of this entry+key pair or pDefault if the entry+key + * pair doesn't exist + **/ + QString readEntry(int entry, const QString& key, const QString& pDefault = QString::null) const; + + /** + * Read a numeric value. + * @param entry The number of the entry / the placing to be read + * @param key The key of the entry. E.g. "name" for the name of the + * player. Nearly the same as the usual keys in KConfig - but they + * are prefixed with the entry number + * @param pDefault This will be used as default value if the key+pair + * entry can't be found. + * @return The value of this entry+key pair or pDefault if the entry+key + * pair doesn't exist + **/ + int readNumEntry(int entry, const QString& key, int pDefault = -1) const; + + /** + * Read a QVariant entry. + * See KConfigBase documentation for allowed QVariant::Type. + * + * @return the value of this entry+key pair or pDefault if the entry+key + * pair doesn't exist or + */ + QVariant readPropertyEntry(int entry, const QString &key, const QVariant &pDefault) const; + + /** + * @return True if the highscore table conatins the entry/key pair, + * otherwise false + **/ + bool hasEntry(int entry, const QString& key) const; + + /** + * Reads a list of entries from the highscore table starting at 1 until + * lastEntry. If an entry between those numbers doesn't exist the + * function aborts reading even if after the missing entry is an + * existing one. The first entry of the list is the first placing, the + * last on is the last placing. + * @return A list of the entries of this key. You could also call + * readEntry(i, key) where i is from 1 to 20. Note that this function + * depends on "1" as the first entry! + * @param key The key of the entry. E.g. "name" for the name of the + * player. Nearly the same as the usual keys in KConfig - but they + * are prefixed with the entry number + * @param lastEntry the last entry which will be includes into the list. + * 1 will include a list with maximal 1 entry - 20 a list with maximal + * 20 entries. If lastEntry is <= 0 then rading is only stopped when when an + * entry does not exist. + **/ + QStringList readList(const QString& key, int lastEntry = 20) const; + + /** + * Writes a list of entries to the highscore table. + * + * The first entry is prefixed with "1". Using this method is a short + * way of calling writeEntry(i, key, list[i]) from i = 1 to + * list.count() + * @param key A key for the entry. E.g. "name" for the name of the + * player. Nearly the same as the usual keys in KConfig - but they + * are prefixed with the entry number + * @param list The list of values + **/ + void writeList(const QString& key, const QStringList& list); + + /** + * @return Whether a highscore table exists. You can use this + * function to indicate whether KHighscore created a highscore table + * before and - if not - read your old (non-KHighscore) table instead. + * This way you can safely read an old table and save it using + * KHighscore without losing any data + **/ + bool hasTable() const; + + /** @obsolete + * This does the same as writeAndUnlock(). + */ + void sync(); + + /** + * Set the new highscore group. The group is being prefixed with + * "KHighscore_" in the table. + * @param groupname The new groupname. E.g. use "easy" for the easy + * level of your game. If you use QString::null (the default) the + * default group is used. + **/ + void setHighscoreGroup(const QString& groupname = QString::null); + + /** + * @return The currently used group. This doesn't contain the prefix + * ("KHighscore_") but the same as setHighscoreGroup uses. The + * default is QString::null + **/ + const QString& highscoreGroup() const; + +protected: + /** + * @return A groupname to be used in KConfig. Used internally to + * prefix the value from highscoreGroup() with "KHighscore_" + **/ + QString group() const; + + /** + * @return A pointer to the KConfig object to be used. This is + * either kapp->config() (default) or a KSimpleConfig object for + * a system-wide highscore file. + **/ + KConfig* config() const; + + void init(bool forceLocal); + +private: + KHighscorePrivate* d; + + static KFileLock *_lock; // lock on system-wide highscore file + static KRawConfig *_config; // config for system-wide highscore file +}; + +#endif |