File indexing completed on 2024-12-22 03:45:40

0001 /*
0002     SPDX-FileCopyrightText: 2010 Marco Martin <mart@kde.org>
0003     SPDX-FileCopyrightText: 2014 David Edmundson <davidedmundson@kde.org>
0004 
0005     SPDX-License-Identifier: GPL-2.0-or-later
0006 */
0007 #ifndef FRAMESVGITEM_P
0008 #define FRAMESVGITEM_P
0009 
0010 #include <QQmlParserStatus>
0011 #include <QQuickItem>
0012 
0013 #include <KSvg/FrameSvg>
0014 
0015 namespace Kirigami
0016 {
0017 namespace Platform
0018 {
0019 class PlatformTheme;
0020 }
0021 };
0022 
0023 namespace KSvg
0024 {
0025 class FrameSvg;
0026 
0027 /**
0028  * @class FrameSvgItemMargins
0029  *
0030  * @short The sizes of a frame's margins.
0031  */
0032 class FrameSvgItemMargins : public QObject
0033 {
0034     Q_OBJECT
0035 
0036     /**
0037      * @brief This property holds the left margin's width in pixels.
0038      * @property real left
0039      */
0040     Q_PROPERTY(qreal left READ left NOTIFY marginsChanged)
0041 
0042     /**
0043      * @brief This property holds the top margin's width in pixels.
0044      * @property real top
0045      */
0046     Q_PROPERTY(qreal top READ top NOTIFY marginsChanged)
0047 
0048     /**
0049      * @brief This property holds the right margin's width in pixels.
0050      * @property real right
0051      */
0052     Q_PROPERTY(qreal right READ right NOTIFY marginsChanged)
0053 
0054     /**
0055      * @brief This property holds the bottom margin's width in pixels.
0056      * @property real bottom
0057      */
0058     Q_PROPERTY(qreal bottom READ bottom NOTIFY marginsChanged)
0059 
0060     /**
0061      * @brief This property holds the combined width of the left and right margins.
0062      * @property real horizontal
0063      */
0064     Q_PROPERTY(qreal horizontal READ horizontal NOTIFY marginsChanged)
0065 
0066     /**
0067      * @brief This property holds the combined width of the top and bottom margins.
0068      * @property real vertical
0069      */
0070     Q_PROPERTY(qreal vertical READ vertical NOTIFY marginsChanged)
0071 
0072 public:
0073     FrameSvgItemMargins(KSvg::FrameSvg *frameSvg, QObject *parent = nullptr);
0074 
0075     qreal left() const;
0076     qreal top() const;
0077     qreal right() const;
0078     qreal bottom() const;
0079     qreal horizontal() const;
0080     qreal vertical() const;
0081 
0082     /// returns a vector with left, top, right, bottom
0083     QList<qreal> margins() const;
0084 
0085     void setFixed(bool fixed);
0086     bool isFixed() const;
0087 
0088     void setInset(bool inset);
0089     bool isInset() const;
0090 
0091 public Q_SLOTS:
0092     void update();
0093 
0094 Q_SIGNALS:
0095     void marginsChanged();
0096 
0097 private:
0098     FrameSvg *m_frameSvg;
0099     bool m_fixed;
0100     bool m_inset;
0101 };
0102 
0103 /**
0104  * @class FrameSvgItem
0105  * @short An SVG Item with borders.
0106  * @import org.kde.ksvg
0107  */
0108 class FrameSvgItem : public QQuickItem
0109 {
0110     Q_OBJECT
0111     Q_INTERFACES(QQmlParserStatus)
0112 
0113     /**
0114      * @brief This property specifies the relative path of the SVG in the theme.
0115      *
0116      * Example: "widgets/background"
0117      *
0118      * @property QString imagePath
0119      */
0120     Q_PROPERTY(QString imagePath READ imagePath WRITE setImagePath NOTIFY imagePathChanged)
0121 
0122     /**
0123      * This property holds the prefix for the SVG.
0124      * prefix for the 9-piece SVG, like "pushed" or "normal" for a button.
0125      * see https://techbase.kde.org/Development/Tutorials/Plasma5/ThemeDetails
0126      * for a list of paths and prefixes
0127      * It can also be an array of strings, specifying a fallback chain in case
0128      * the first element isn't found in the theme, eg ["toolbutton-normal", "normal"]
0129      * so it's easy to keep backwards compatibility with old themes
0130      * (Note: fallback chain is supported only @since 5.32)
0131      */
0132     Q_PROPERTY(QVariant prefix READ prefix WRITE setPrefix NOTIFY prefixChanged)
0133 
0134     /**
0135      * @brief This property holds the actual prefix that was used, if a fallback
0136      * chain array was set as "prefix".
0137      *
0138      * @since 5.34
0139      * @property QString usedPrefix
0140      */
0141     Q_PROPERTY(QString usedPrefix READ usedPrefix NOTIFY usedPrefixChanged)
0142 
0143     /**
0144      * @brief This property holds the frame's margins.
0145      * @see FrameSvgItemMargins
0146      * @property FrameSvgItemMargins margins
0147      */
0148     Q_PROPERTY(FrameSvgItemMargins *margins READ margins CONSTANT)
0149 
0150     /**
0151      * @brief This property holds the fixed margins of the frame which are used
0152      * regardless of any margins being enabled or not.
0153      *
0154      * @see FrameSvgItemMargins
0155      * @property FrameSvgItemMargins margins
0156      */
0157     Q_PROPERTY(FrameSvgItemMargins *fixedMargins READ fixedMargins CONSTANT)
0158 
0159     /**
0160      * @brief This property holds the frame's inset.
0161      *
0162      * @see FrameSvgItemMargins
0163      *
0164      * @since 5.77
0165      * @property FrameSvgItemMargins margins
0166      */
0167     Q_PROPERTY(FrameSvgItemMargins *inset READ inset CONSTANT)
0168 
0169     /**
0170      * @brief This property specifies which borders are shown.
0171      * @see KSvg::FrameSvg::EnabledBorder
0172      * @property flags<KSvg::FrameSvg::EnabledBorder> enabledBorders
0173      */
0174     Q_PROPERTY(KSvg::FrameSvg::EnabledBorders enabledBorders READ enabledBorders WRITE setEnabledBorders NOTIFY enabledBordersChanged)
0175 
0176     /**
0177      * @brief This property holds whether the current SVG is present in
0178      * the currently-used theme and no fallback is involved.
0179      */
0180     Q_PROPERTY(bool fromCurrentImageSet READ fromCurrentImageSet NOTIFY fromCurrentImageSetChanged)
0181 
0182     /**
0183      * @brief This property specifies the SVG's status.
0184      *
0185      * Depending on the specified status, the SVG will use different colors:
0186      * * Normal: text's color is textColor, and background color is
0187      * backgroundColor.
0188      * * Selected: text color becomes highlightedText and background color is
0189      * changed to highlightColor.
0190      *
0191      * @see Kirigami::PlatformTheme
0192      * @see KSvg::Svg::status
0193      * @since 5.23
0194      * @property enum<KSvg::Svg::Status> status
0195      */
0196     Q_PROPERTY(KSvg::Svg::Status status READ status WRITE setStatus NOTIFY statusChanged)
0197 
0198     /**
0199      * @brief This property holds the mask that contains the SVG's painted areas.
0200      * @since 5.58
0201      * @property QRegion mask
0202      */
0203     Q_PROPERTY(QRegion mask READ mask NOTIFY maskChanged)
0204 
0205     /**
0206      * @brief This property holds the minimum height required to correctly draw
0207      * this SVG.
0208      *
0209      * @since 5.101
0210      * @property int minimumDrawingHeight
0211      */
0212     Q_PROPERTY(int minimumDrawingHeight READ minimumDrawingHeight NOTIFY repaintNeeded)
0213 
0214     /**
0215      * @brief This property holds the minimum width required to correctly draw
0216      * this SVG.
0217      *
0218      * @since 5.101
0219      * @property int minimumDrawingWidth
0220      */
0221     Q_PROPERTY(int minimumDrawingWidth READ minimumDrawingWidth NOTIFY repaintNeeded)
0222 
0223 public:
0224     /**
0225      * @return whether the svg has the necessary elements with the given prefix
0226      * to draw a frame.
0227      *
0228      * @param prefix the given prefix we want to check if drawable
0229      */
0230     Q_INVOKABLE bool hasElementPrefix(const QString &prefix) const;
0231 
0232     /**
0233      * @return whether the SVG includes the given element.
0234      *
0235      * This is a convenience function that forwards to hasElement().
0236      *
0237      * @see KSvg::Svg::hasElement()
0238      */
0239     Q_INVOKABLE bool hasElement(const QString &elementName) const;
0240 
0241     /// @cond INTERNAL_DOCS
0242     FrameSvgItem(QQuickItem *parent = nullptr);
0243     ~FrameSvgItem() override;
0244 
0245     void setImagePath(const QString &path);
0246     QString imagePath() const;
0247 
0248     void setPrefix(const QVariant &prefix);
0249     QVariant prefix() const;
0250 
0251     QString usedPrefix() const;
0252 
0253     void setEnabledBorders(const KSvg::FrameSvg::EnabledBorders borders);
0254     KSvg::FrameSvg::EnabledBorders enabledBorders() const;
0255 
0256     void setColorSet(KSvg::Svg::ColorSet colorSet);
0257     KSvg::Svg::ColorSet colorSet() const;
0258 
0259     FrameSvgItemMargins *margins();
0260     FrameSvgItemMargins *fixedMargins();
0261     FrameSvgItemMargins *inset();
0262 
0263     bool fromCurrentImageSet() const;
0264 
0265     void setStatus(KSvg::Svg::Status status);
0266     KSvg::Svg::Status status() const;
0267     int minimumDrawingHeight() const;
0268     int minimumDrawingWidth() const;
0269 
0270     void geometryChange(const QRectF &newGeometry, const QRectF &oldGeometry) override;
0271 
0272     QRegion mask() const;
0273 
0274     /**
0275      * Only to be used from inside this library, is not intended to be invokable
0276      */
0277     KSvg::FrameSvg *frameSvg() const;
0278 
0279     QSGNode *updatePaintNode(QSGNode *, UpdatePaintNodeData *) override;
0280 
0281     void itemChange(QQuickItem::ItemChange change, const QQuickItem::ItemChangeData &data) override;
0282 
0283 protected:
0284     void classBegin() override;
0285     void componentComplete() override;
0286 
0287     /// @endcond
0288 
0289 Q_SIGNALS:
0290     void imagePathChanged();
0291     void prefixChanged();
0292     void enabledBordersChanged();
0293     void fromCurrentImageSetChanged();
0294     void repaintNeeded();
0295     void statusChanged();
0296     void usedPrefixChanged();
0297     void maskChanged();
0298 
0299 private Q_SLOTS:
0300     void doUpdate();
0301 
0302 private:
0303     void updateDevicePixelRatio();
0304     void applyPrefixes();
0305 
0306     KSvg::FrameSvg *m_frameSvg;
0307     Kirigami::Platform::PlatformTheme *m_kirigamiTheme;
0308     FrameSvgItemMargins *m_margins;
0309     FrameSvgItemMargins *m_fixedMargins;
0310     FrameSvgItemMargins *m_insetMargins;
0311     // logged margins to check for changes
0312     QList<qreal> m_oldMargins;
0313     QList<qreal> m_oldFixedMargins;
0314     QList<qreal> m_oldInsetMargins;
0315     QStringList m_prefixes;
0316     bool m_textureChanged;
0317     bool m_sizeChanged;
0318     bool m_fastPath;
0319 };
0320 
0321 }
0322 
0323 #endif