Perceptual Color

chromalightnessdiagram_p.h
1// SPDX-FileCopyrightText: Lukas Sommer <sommerluk@gmail.com>
2// SPDX-License-Identifier: BSD-2-Clause OR MIT
3
4#ifndef CHROMALIGHTNESSDIAGRAM_P_H
5#define CHROMALIGHTNESSDIAGRAM_P_H
6
7// Include the header of the public class of this private implementation.
8// #include "chromalightnessdiagram.h"
9
10#include "asyncimageprovider.h"
11#include "chromalightnessimageparameters.h"
12#include "constpropagatingrawpointer.h"
13#include "lchdouble.h"
14#include <cmath>
15#include <functional>
16#include <limits>
17#include <optional>
18#include <qglobal.h>
19#include <qsharedpointer.h>
20#include <qsize.h>
21class QRect;
22class QPoint;
23
24namespace PerceptualColor
25{
26class ChromaLightnessDiagram;
27class RgbColorSpace;
28
29/** @internal
30 *
31 * @brief Private implementation within the <em>Pointer to
32 * implementation</em> idiom */
33class ChromaLightnessDiagramPrivate final
34{
35public:
36 explicit ChromaLightnessDiagramPrivate(ChromaLightnessDiagram *backLink);
37 /** @brief Default destructor
38 *
39 * The destructor is non-<tt>virtual</tt> because
40 * the class as a whole is <tt>final</tt>. */
41 ~ChromaLightnessDiagramPrivate() noexcept = default;
42
43 // Member variables
44 /** @brief The image of the chroma-lightness diagram itself. */
45 AsyncImageProvider<ChromaLightnessImageParameters> m_chromaLightnessImage;
46 /** @brief Properties for @ref m_chromaLightnessImage. */
47 ChromaLightnessImageParameters m_chromaLightnessImageParameters;
48 /** @brief Internal storage of
49 * the @ref ChromaLightnessDiagram::currentColor property */
50 LchDouble m_currentColor;
51 /** @brief Holds if currently a mouse event is active or not.
52 *
53 * Default value is <tt>false</tt>.
54 * - A mouse event gets typically activated on a
55 * @ref ChromaLightnessDiagram::mousePressEvent()
56 * done within the gamut diagram. The value is set to <tt>true</tt>.
57 * - While active, all @ref ChromaLightnessDiagram::mouseMoveEvent() will
58 * move the diagram’s color handle.
59 * - Once a @ref ChromaLightnessDiagram::mouseReleaseEvent() occurs, the
60 * value is set to <tt>false</tt>. Further mouse movements will not
61 * move the handle anymore.
62 *
63 * This is done because Qt’s default mouse tracking reacts on all clicks
64 * within the (rectangular) widget. However, <em>this</em> widget is meant
65 * as a circular widget, only reacting on mouse events within the circle;
66 * this requires this custom implementation. */
67 bool m_isMouseEventActive = false; // TODO Remove me!
68 /** @brief Pointer to RgbColorSpace() object */
69 QSharedPointer<RgbColorSpace> m_rgbColorSpace;
70
71 // Member functions
72 [[nodiscard]] QSize calculateImageSizePhysical() const;
73 [[nodiscard]] int defaultBorderPhysical() const;
74 /** @internal
75 *
76 * @brief Calculate how far a value is from a given range.
77 * @pre <tt>low</tt> ≤ <tt>high</tt>
78 * @param low the lower limit
79 * @param x the value that will be tested
80 * @param high the higher limit
81 * @returns <tt>0</tt> if the value is within the range. The distance
82 * to the nearest border of the range otherwise. */
83 template<typename T>
84 [[nodiscard]] static constexpr T distanceFromRange(const T &low, const T &x, const T &high)
85 {
86 if (x < low) {
87 return low - x;
88 }
89 if (x > high) {
90 return x - high;
91 }
92 if constexpr ( //
93 std::numeric_limits<T>::has_quiet_NaN //
94 || std::numeric_limits<T>::has_signaling_NaN //
95 ) {
96 if (std::isnan(low) || std::isnan(x) || std::isnan(high)) {
97 return std::numeric_limits<T>::quiet_NaN();
98 }
99 }
100 return 0;
101 }
102 [[nodiscard]] LchDouble fromWidgetPixelPositionToColor(const QPoint widgetPixelPosition) const;
103 [[nodiscard]] bool isWidgetPixelPositionInGamut(const QPoint widgetPixelPosition) const;
104 [[nodiscard]] int leftBorderPhysical() const;
105 [[nodiscard]] PerceptualColor::LchDouble nearestInGamutColorByAdjustingChromaLightness(const double chroma, const double lightness);
106 [[nodiscard]] std::optional<QPoint> nearestInGamutPixelPosition(const QPoint originalPixelPosition);
107 [[nodiscard]] static std::optional<QPoint>
108 nearestNeighborSearch(const QPoint point, const QRect searchRectangle, const std::function<bool(const QPoint)> &doesPointExist);
109 void setCurrentColorFromWidgetPixelPosition(const QPoint widgetPixelPosition);
110
111private:
112 Q_DISABLE_COPY(ChromaLightnessDiagramPrivate)
113
114 /** @brief Pointer to the object from which <em>this</em> object
115 * is the private implementation. */
116 ConstPropagatingRawPointer<ChromaLightnessDiagram> q_pointer;
117};
118
119} // namespace PerceptualColor
120
121#endif // CHROMALIGHTNESSDIAGRAM_P_H
The namespace of this library.
A LCH color (Oklch, CielchD50, CielchD65…)
Definition lchdouble.h:50
This file is part of the KDE documentation.
Documentation copyright © 1996-2024 The KDE developers.
Generated on Fri May 24 2024 11:48:43 by doxygen 1.10.0 written by Dimitri van Heesch, © 1997-2006

KDE's Doxygen guidelines are available online.