Krita Source Code Documentation
Loading...
Searching...
No Matches
kis_four_point_interpolator_backward.h
Go to the documentation of this file.
1/*
2 * SPDX-FileCopyrightText: 2014 Dmitry Kazakov <dimula73@gmail.com>
3 *
4 * SPDX-License-Identifier: GPL-2.0-or-later
5 */
6
7#ifndef __KIS_FOUR_POINT_INTERPOLATOR_BACKWARD_H
8#define __KIS_FOUR_POINT_INTERPOLATOR_BACKWARD_H
9
10#include <QPolygon>
11#include <QPointF>
12
13#include "kis_global.h"
14#include "kis_algebra_2d.h"
15
16
25{
26public:
27 KisFourPointInterpolatorBackward(const QPolygonF &srcPolygon, const QPolygonF &dstPolygon) {
28 m_a = dstPolygon[1] - dstPolygon[0]; // AB
29 m_b = dstPolygon[2] - dstPolygon[1]; // BD
30 m_c = dstPolygon[3] - dstPolygon[0]; // AC
31 m_d = m_b - m_c; // BD - AC
32
33 m_qA = m_c.x() * m_d.y() - m_c.y() * m_d.x();
34
35 m_srcBase = srcPolygon[0];
36 m_dstBase = dstPolygon[0];
37 m_xCoeff = srcPolygon[1].x() - srcPolygon[0].x(); // AB_src
38 m_yCoeff = srcPolygon[3].y() - srcPolygon[0].y(); // AC_src
39
40 m_qB_const = m_c.x() * m_a.y() - m_c.y() * m_a.x();
41
42 m_qD_div = 1.0 / (2 * m_qA);
43
44 //m_qB_varX = 0.0;
45 //m_qB_varY = 0.0;
46 }
47
52 inline bool isValid(const qreal tolerance = 0.1) const {
53 const qreal toleranceSq = pow2(tolerance);
54
55 const qreal sq1 = qAbs(m_qB_const);
56 const qreal sq2 = qAbs(KisAlgebra2D::crossProduct(m_b, m_c - m_b + m_a));
57
58 return sq1 + sq2 > 2 * toleranceSq;
59 }
60
61 inline QPointF fallbackSourcePoint() const {
62 return m_srcBase + QPointF(0.5 * m_xCoeff, 0.5 * m_yCoeff);
63 }
64
65 inline QPointF map(const QPointF &pt) {
66 setX(pt.x());
67 setY(pt.y());
68 return getValue();
69 }
70
71 inline void setX(qreal x) {
72 x -= m_dstBase.x();
73
74 m_qB_varX = - x * m_d.y();
75 m_qC_varX = - x * m_a.y();
76 m_px = x;
77 }
78
79 inline void setY(qreal y) {
80 y -= m_dstBase.y();
81
82 m_qB_varY = y * m_d.x();
83 m_qC_varY = y * m_a.x();
84 m_py = y;
85 }
86
87 inline QPointF getValue() const {
88 static const qreal eps = 1e-10;
89
90 qreal qB = m_qB_const + m_qB_varX + m_qB_varY;
91 qreal qC = m_qC_varX + m_qC_varY;
92
93 qreal nu = 0.0;
94
95 if (qAbs(m_qA) < eps) {
96 nu = -qC / qB;
97 } else {
98 qreal D = pow2(qB) - 4 * m_qA * qC;
99 if (D > 0.0) {
100 qreal sqrtD = std::sqrt(D);
101 nu = (-qB - sqrtD) * m_qD_div;
102 if (nu < 0.0 || nu > 1.0) {
103 qreal nu2 = (-qB + sqrtD) * m_qD_div;
104
105 if (nu2 < 0.0 || nu2 > 1.0) {
106 nu = qBound(qreal(0.0), nu, qreal(1.0));
107 } else {
108 nu = nu2;
109 }
110 }
111 } else {
112 nu = 0.0;
113 }
114 }
115
116 qreal xBasedDenominator = m_a.x() + nu * m_d.x();
117
118 qreal mu;
119
120 if (qAbs(xBasedDenominator) > eps) {
121 mu = (m_px - nu * m_c.x()) / xBasedDenominator;
122 } else {
123 mu = (m_py - nu * m_c.y()) / (m_a.y() + nu * m_d.y());
124 }
125
126 return m_srcBase + QPointF(mu * m_xCoeff, nu * m_yCoeff);
127 }
128
129private:
130 QPointF m_a; // AB
131 QPointF m_b; // BD
132 QPointF m_c; // AC
133 QPointF m_d; // m_b - m_c
134
135 qreal m_qA {0.0}; // quadratic equation A coeff
136 qreal m_qB_const {0.0}; // quadratic equation B coeff, const part
137 qreal m_qB_varX {0.0}; // quadratic equation B coeff, X-dep part
138 qreal m_qB_varY {0.0}; // quadratic equation B coeff, Y-dep part
139 qreal m_qC_varX {0.0}; // quadratic equation C coeff, X-dep part
140 qreal m_qC_varY {0.0}; // quadratic equation C coeff, Y-dep part
141 qreal m_qD_div {0.0}; // inverted divisor of the quadratic equation solution
142 qreal m_px {0.0}; // saved relative X coordinate
143 qreal m_py {0.0}; // saved relative Y coordinate
144
145 QPointF m_srcBase;
146 QPointF m_dstBase;
147 qreal m_xCoeff {0.0};
148 qreal m_yCoeff {0.0};
149};
150
151#endif /* __KIS_FOUR_POINT_INTERPOLATOR_BACKWARD_H */
qreal D(qreal t, const QPointF &P0, const QPointF &P1, const QPointF &P2, const QPointF &P3, const QPointF &p)
bool isValid(const qreal tolerance=0.1) const
KisFourPointInterpolatorBackward(const QPolygonF &srcPolygon, const QPolygonF &dstPolygon)
const qreal eps
T pow2(const T &x)
Definition kis_global.h:166
PointTypeTraits< T >::value_type crossProduct(const T &a, const T &b)