File indexing completed on 2024-05-19 04:32:39

0001 /*
0002  *  SPDX-FileCopyrightText: 2023 Dmitry Kazakov <dimula73@gmail.com>
0003  *
0004  *  SPDX-License-Identifier: GPL-2.0-or-later
0005  */
0006 
0007 #include "KisDumbTransformMaskParams.h"
0008 
0009 #include <QDomElement>
0010 #include "kis_algebra_2d.h"
0011 #include "kis_dom_utils.h"
0012 #include "kis_node.h"
0013 #include "kis_painter.h"
0014 
0015 
0016 struct Q_DECL_HIDDEN KisDumbTransformMaskParams::Private
0017 {
0018     Private() : isHidden(false) {}
0019 
0020     QTransform transform;
0021     bool isHidden;
0022 };
0023 
0024 KisDumbTransformMaskParams::KisDumbTransformMaskParams()
0025     : m_d(new Private)
0026 {
0027 }
0028 
0029 KisDumbTransformMaskParams::KisDumbTransformMaskParams(const QTransform &transform)
0030     : m_d(new Private)
0031 {
0032     m_d->isHidden = false;
0033     m_d->transform = transform;
0034 }
0035 
0036 KisDumbTransformMaskParams::KisDumbTransformMaskParams(bool isHidden)
0037     : m_d(new Private)
0038 {
0039     m_d->isHidden = isHidden;
0040 }
0041 
0042 KisDumbTransformMaskParams::~KisDumbTransformMaskParams()
0043 {
0044 }
0045 
0046 QTransform KisDumbTransformMaskParams::finalAffineTransform() const
0047 {
0048     return m_d->transform;
0049 }
0050 
0051 bool KisDumbTransformMaskParams::isAffine() const
0052 {
0053     return true;
0054 }
0055 
0056 bool KisDumbTransformMaskParams::isHidden() const
0057 {
0058     return m_d->isHidden;
0059 }
0060 
0061 void KisDumbTransformMaskParams::setHidden(bool value)
0062 {
0063     m_d->isHidden = value;
0064 }
0065 
0066 void KisDumbTransformMaskParams::transformDevice(KisNodeSP node, KisPaintDeviceSP src, KisPaintDeviceSP dst, bool forceSubPixelTranslation) const
0067 {
0068     Q_UNUSED(node);
0069     Q_UNUSED(forceSubPixelTranslation);
0070 
0071     QRect rc = src->exactBounds();
0072     QPoint dstTopLeft = rc.topLeft();
0073 
0074     QTransform t = finalAffineTransform();
0075     if (t.isTranslating()) {
0076         dstTopLeft = t.map(dstTopLeft);
0077     } else if (!t.isIdentity()) {
0078         warnKrita << "KisDumbTransformMaskParams::transformDevice does not support this kind of transformation";
0079         warnKrita << ppVar(t);
0080     }
0081 
0082     KisPainter::copyAreaOptimized(dstTopLeft, src, dst, rc);
0083 }
0084 
0085 QString KisDumbTransformMaskParams::id() const
0086 {
0087     return "dumbparams";
0088 }
0089 
0090 void KisDumbTransformMaskParams::toXML(QDomElement *e) const
0091 {
0092     QDomDocument doc = e->ownerDocument();
0093     QDomElement transformEl = doc.createElement("dumb_transform");
0094     e->appendChild(transformEl);
0095 
0096     KisDomUtils::saveValue(&transformEl, "transform", m_d->transform);
0097 }
0098 
0099 KisTransformMaskParamsInterfaceSP KisDumbTransformMaskParams::fromXML(const QDomElement &e)
0100 {
0101     QDomElement transformEl;
0102     bool result = false;
0103 
0104     QTransform transform;
0105 
0106     result =
0107         KisDomUtils::findOnlyElement(e, "dumb_transform", &transformEl) &&
0108         KisDomUtils::loadValue(transformEl, "transform", &transform);
0109 
0110     if (!result) {
0111         warnKrita << "WARNING: couldn't load dumb transform. Ignoring...";
0112     }
0113 
0114     return KisTransformMaskParamsInterfaceSP(
0115         new KisDumbTransformMaskParams(transform));
0116 }
0117 
0118 void KisDumbTransformMaskParams::translateSrcAndDst(const QPointF &offset)
0119 {
0120     Q_UNUSED(offset);
0121 
0122     /**
0123      * Normal translation doesn't change affine transformations
0124      * in full-featured KisTransformMaskAdapter, so we should resemble
0125      * this behavior in the dumb one
0126      */
0127 }
0128 
0129 void KisDumbTransformMaskParams::transformSrcAndDst(const QTransform &t)
0130 {
0131     Q_UNUSED(t);
0132 
0133     /**
0134      * Normal translation doesn't change affine transformations
0135      * in full-featured KisTransformMaskAdapter, so we should resemble
0136      * this behavior in the dumb one
0137      */
0138 }
0139 
0140 void KisDumbTransformMaskParams::translateDstSpace(const QPointF &offset)
0141 {
0142     m_d->transform.translate(offset.x(), offset.y());
0143 }
0144 
0145 QRect KisDumbTransformMaskParams::nonAffineChangeRect(const QRect &rc)
0146 {
0147     return rc;
0148 }
0149 
0150 QRect KisDumbTransformMaskParams::nonAffineNeedRect(const QRect &rc, const QRect &srcBounds)
0151 {
0152     Q_UNUSED(srcBounds);
0153     return rc;
0154 }
0155 
0156 bool KisDumbTransformMaskParams::isAnimated() const
0157 {
0158     return false;
0159 }
0160 
0161 KisKeyframeChannel *KisDumbTransformMaskParams::getKeyframeChannel(const QString&, KisDefaultBoundsBaseSP)
0162 {
0163     return 0;
0164 }
0165 
0166 KisTransformMaskParamsInterfaceSP KisDumbTransformMaskParams::clone() const
0167 {
0168     return toQShared(new KisDumbTransformMaskParams(m_d->transform));
0169 }
0170 
0171 bool KisDumbTransformMaskParams::compareTransform(KisTransformMaskParamsInterfaceSP rhs) const
0172 {
0173     QSharedPointer<KisDumbTransformMaskParams> rhsParams =
0174             rhs.dynamicCast<KisDumbTransformMaskParams>();
0175 
0176     return KisAlgebra2D::fuzzyMatrixCompare(m_d->transform, rhsParams->m_d->transform, 1e-5);
0177 }
0178 
0179 QTransform KisDumbTransformMaskParams::testingGetTransform() const
0180 {
0181     return m_d->transform;
0182 }
0183 
0184 void KisDumbTransformMaskParams::testingSetTransform(const QTransform &t)
0185 {
0186     m_d->transform = t;
0187 }