File indexing completed on 2024-04-21 04:05:25

0001 /*
0002     This file is part of the KDE games lskat program
0003     SPDX-FileCopyrightText: 2006 Martin Heni <kde@heni-online.de>
0004 
0005     SPDX-License-Identifier: LGPL-2.0-or-later
0006 */
0007 
0008 #ifndef THEME_MANAGER_H
0009 #define THEME_MANAGER_H
0010 
0011 // Qt includes
0012 #include <QObject>
0013 #include <QHash>
0014 #include <QSvgRenderer>
0015 
0016 // KF includes
0017 #include <KConfig>
0018 
0019 class KCardCache;
0020 class ThemeManager;
0021 
0022 /**
0023  * Objects which are connected to the theme manger must inherit
0024  * from this class. Doing so enables the items to be refreshed
0025  * by the theme manager and allows them to retrieve theme data
0026  * from a configuration theme file.
0027  */
0028 class Themable
0029 {
0030 public:
0031     /**
0032      * Default constructor for the interface
0033      */
0034     Themable();
0035 
0036     /**
0037      * Constructor for the interface given the theme item unique ID string
0038      * and a reference to the theme manager. The ID string is used to refer
0039      * to the group in the configuration file.
0040      * @param id           The user defined theme id
0041      * @param thememanager The used theme manager
0042      */
0043     Themable(const QString &id, ThemeManager *thememanager);
0044 
0045     /**
0046      * Destructor
0047      */
0048     virtual ~Themable();
0049 
0050     /**
0051      * Retrieve the ID of the object.
0052      * @return The ID.
0053      */
0054     QString id() {return mId;}
0055 
0056     /**
0057      * Retrieve the associated theme manager of this object.
0058      * @return The theme manager.
0059      */
0060     ThemeManager *thememanager() {return mThemeManager;}
0061 
0062     /**
0063      * Retrieve the current scale (maximum extension) of the theme.
0064      * @return The current scale.
0065      */
0066     double getScale() {return mScale;}
0067 
0068     /**
0069      * Set the current scale for the object.
0070      * @param scale The new scale.
0071      */
0072     void setScale(double scale) {mScale = scale;}
0073 
0074     /**
0075      * Main theme notification method. This method is called in the
0076      * Themable object to indicate a theme change. The object needs
0077      * to overwrite this and respond with a properly scaled redraw.
0078      */
0079     virtual void changeTheme() = 0;
0080 
0081 private:
0082     // The theme ID
0083     QString mId;
0084 
0085     // The theme manager
0086     ThemeManager *mThemeManager;
0087 
0088     // The current scale for the object (maximum extension)
0089     double mScale;
0090 };
0091 
0092 /**
0093  * The graphics theme manager. The theme manager holds a list of all Themable
0094  * objects and notifies them in the event of a theme change so that the objects
0095  * can then redraw. It also allows access to the theme configuration file and
0096  * reads pixmaps from an SVG file given a certain size or scale. The pixmaps
0097  * are cached so that the same pixmap is retrieved from the cache on not
0098  * rendered again.
0099  */
0100 class ThemeManager : public QObject
0101 {
0102     Q_OBJECT
0103 public:
0104     /**
0105      * Constructor for the theme manager.
0106      * @param cardTheme   card theme
0107      * @param themefile   The theme configuration file
0108      * @param parent      The parent object
0109      * @param initialSize Initial theme size, can be arbitrary.
0110      */
0111     ThemeManager(const QString &cardTheme, const QString &themefile,
0112                  QObject *parent, int initialSize = 1);
0113 
0114     ~ThemeManager() override;
0115     /**
0116      * Get the pixmap for a card.
0117      * @param suite    The suite of the card [Club, ...]
0118      * @param cardtype The type of the card [Ace, ...]
0119      * @return The new pixmap.
0120      */
0121     const QPixmap getCard(int suite, int cardtype, double width);
0122 
0123     /**
0124      * Get a backside of the card.
0125      * @param width    The width of the card back [pixels]
0126      * @return The new pixmap.
0127      */
0128     const QPixmap getCardback(double width);
0129 
0130     /**
0131      * Load a pixmap from the SVG theme file. Its filename is given in the
0132      * "general" section of the theme file as "svgfile". The pixmap is scaled
0133      * to the given size.
0134      * @param svgid  The ID of the SVG item to be rendered as pixmap
0135      * @param size   The size of the resulting pixmap
0136      * @return The new pixmap.
0137      */
0138     const QPixmap getPixmap(const QString &svgid, const QSize &size);
0139 
0140     /**
0141      * Load a pixmap from the SVG theme file. Its filename is given in the
0142      * "general" section of the theme file as "svgfile". The pixmap is scaled
0143      * to the given width. The height is relative to the width as given in the
0144      * SVG file.
0145      * @param svgid  The ID of the SVG item to be rendered as pixmap
0146      * @param width  The width of the resulting pixmap
0147      * @return The new pixmap.
0148      */
0149     const QPixmap getPixmap(const QString &svgid, double width);
0150 
0151     /**
0152      * Load a pixmap from the SVG theme file. Its filename is given in the
0153      * "general" section of the theme file as "svgfile". The pixmap is scaled
0154      * with reference to another SVG item. This allows to generate a set of
0155      * pixmaps with related sizes.
0156      * @param svgid     The ID of the SVG item to be rendered as pixmap
0157      * @param svgref    The ID of the SVG item used as width reference
0158      * @param refwidth  The width of the resulting pixmap in relation to the reference item
0159      * @return The new pixmap.
0160      */
0161     const QPixmap getPixmap(const QString &svgid, const QString &svgref, double refwidth);
0162 
0163     /**
0164      * Retrieve the current scale of the theme.
0165      * @return The scale.
0166      */
0167     double getScale();
0168 
0169     /**
0170      * Retrieve the theme offset.
0171      * @return The offset.
0172      */
0173     QPoint getOffset();
0174 
0175     /**
0176      * Retrieve the current theme configuration object.
0177      * @return The configuration object.
0178      */
0179     KConfigGroup config(const QString &id);
0180 
0181     /**
0182      * Register an object with the theme manager.
0183      * @param ob The object to be registered.
0184      */
0185     void registerTheme(Themable *ob);
0186 
0187     /**
0188      * Unregister an object with the theme manager.
0189      * @param ob The object to be unregistered.
0190      */
0191     void unregisterTheme(Themable *ob);
0192 
0193     /**
0194      * Forces an update to a theme objects. That is its
0195      * changeTheme() method is called.
0196      * @param ob The object to be updated.
0197      */
0198     void updateTheme(Themable *ob);
0199 
0200     /**
0201      * Forces an update to the card theme objects.
0202      * @param cards The card dir
0203      * @param deckSVG     Filename to the SVG card back (or null string for PNG)
0204      */
0205     void updateCardTheme(const QString &cardTheme);
0206 
0207     /**
0208      * Forces an update to all theme objects. That is their changeTheme() method
0209      * is called. Before this a (new) theme file is loaded and all cached
0210      * pixmaps deleted. This is used to really change one theme over to another
0211      * one.
0212      * @param themefile The theme file to load
0213      */
0214     void updateTheme(const QString &themefile);
0215 
0216     /**
0217      * Change the scale of the theme and update all registered
0218      * theme objects.
0219      * @param scale The new scale (maximum extension)
0220      * @param offset The new offset of the theme (left upper corner)
0221      */
0222     void rescale(int scale, QPoint offset);
0223 
0224     /**
0225      * Retrieve the theme's aspect ratio. This is stored as
0226      * 'aspect-ratio' key in the 'general' group of the theme.
0227      * @return The aspect ratio (x/y).
0228      */
0229     double aspectRatio() {return mAspectRatio;}
0230 
0231     /**
0232      * Check whether the theme is properly initialized.
0233      * @return 0 if everything is alright
0234      */
0235     int checkTheme();
0236 
0237 protected:
0238     /**
0239      * Load a pixmap from the SVG theme file. Its filename is given in the
0240      * "general" section of the theme file as "svgfile". The pixmap is scaled to
0241      * the given size.
0242      * @param renderer The SVG renderer to use
0243      * @param svgid    The ID of the SVG item to be rendered as pixmap
0244      * @param size     The size of the resulting pixmap
0245      * @return The new pixmap.
0246      */
0247     const QPixmap getPixmap(QSvgRenderer *renderer, const QString &svgid, const QSize &size);
0248 
0249     /**
0250      * Forces an update to the card theme objects.
0251      * @param themefile The theme rc file
0252      * @param cards     The card dir
0253      * @param deck      The deck file
0254      * @param deckSVG     Filename to the SVG card back (or null string for PNG)
0255      */
0256     void updateCardTheme(const QString &themefile, const QString &cardTheme);
0257 
0258 private Q_SLOTS:
0259     void loadCardsInBackground();
0260 
0261 private:
0262     // The used SVG rendered
0263     QSvgRenderer *mRenderer;
0264 
0265     // The card cache
0266     KCardCache *mCardCache;
0267 
0268     // Storage of all theme objects [object, 1] [TODO: A list might suffice]
0269     QHash<Themable *, int> mObjects;
0270 
0271     // The cache of all pixmap objects [id, pixmap]
0272     QHash<QString, QPixmap> mPixmapCache;
0273 
0274     // The theme configuration file
0275     KConfig *mConfig;
0276 
0277     // The card configuration file
0278     QString mCardTheme;
0279 
0280     // The current theme scale
0281     int mScale;
0282 
0283     // The current offset
0284     QPoint mOffset;
0285 
0286     // The aspect ration
0287     double mAspectRatio;
0288 
0289     // The card aspect ration
0290     double mCardAspectRatio;
0291 
0292     // The theme file
0293     QString mThemeFile;
0294 };
0295 
0296 #endif