1// Copyright (C) 2016 The Qt Company Ltd.
2// SPDX-License-Identifier: LicenseRef-Qt-Commercial OR LGPL-3.0-only OR GPL-2.0-only OR GPL-3.0-only
3
4#include "qcolortrclut_p.h"
5#include "qcolortransferfunction_p.h"
6#include "qcolortransfergeneric_p.h"
7#include "qcolortransfertable_p.h"
8#include "qcolortrc_p.h"
9#include <qmath.h>
10
11QT_BEGIN_NAMESPACE
12std::shared_ptr<QColorTrcLut> QColorTrcLut::create()
13{
14 struct Access : QColorTrcLut {};
15 return std::make_shared<Access>();
16}
17
18std::shared_ptr<QColorTrcLut> QColorTrcLut::fromGamma(float gamma, Direction dir)
19{
20 auto cp = create();
21 cp->setFromGamma(gamma, dir);
22 return cp;
23}
24
25std::shared_ptr<QColorTrcLut> QColorTrcLut::fromTrc(const QColorTrc &trc, Direction dir)
26{
27 if (!trc.isValid())
28 return nullptr;
29 auto cp = create();
30 cp->setFromTrc(trc, dir);
31 return cp;
32}
33
34void QColorTrcLut::setFromGamma(float gamma, Direction dir)
35{
36 constexpr float iRes = 1.f / float(Resolution);
37 if (dir & ToLinear) {
38 if (!m_toLinear)
39 m_toLinear.reset(p: new ushort[Resolution + 1]);
40 for (int i = 0; i <= Resolution; ++i) {
41 const int val = qRound(f: qPow(x: i * iRes, y: gamma) * (255 * 256));
42 m_toLinear[i] = qBound(min: 0, val, max: 65280);
43 }
44 }
45
46 if (dir & FromLinear) {
47 const float iGamma = 1.f / gamma;
48 if (!m_fromLinear)
49 m_fromLinear.reset(p: new ushort[Resolution + 1]);
50 for (int i = 0; i <= Resolution; ++i)
51 m_fromLinear[i] = ushort(qRound(f: qBound(min: 0.f, val: qPow(x: i * iRes, y: iGamma), max: 1.f) * (255 * 256)));
52 }
53}
54
55void QColorTrcLut::setFromTransferFunction(const QColorTransferFunction &fun, Direction dir)
56{
57 constexpr float iRes = 1.f / float(Resolution);
58 if (dir & ToLinear) {
59 if (!m_toLinear)
60 m_toLinear.reset(p: new ushort[Resolution + 1]);
61 for (int i = 0; i <= Resolution; ++i) {
62 const int val = qRound(f: fun.apply(x: i * iRes)* (255 * 256));
63 if (val > 65280 && i < m_unclampedToLinear)
64 m_unclampedToLinear = i;
65 m_toLinear[i] = qBound(min: 0, val, max: 65280);
66 }
67 }
68
69 if (dir & FromLinear) {
70 if (!m_fromLinear)
71 m_fromLinear.reset(p: new ushort[Resolution + 1]);
72 QColorTransferFunction inv = fun.inverted();
73 for (int i = 0; i <= Resolution; ++i)
74 m_fromLinear[i] = ushort(qRound(f: qBound(min: 0.f, val: inv.apply(x: i * iRes), max: 1.f) * (255 * 256)));
75 }
76}
77
78void QColorTrcLut::setFromTransferGenericFunction(const QColorTransferGenericFunction &fun, Direction dir)
79{
80 constexpr float iRes = 1.f / float(Resolution);
81 if (dir & ToLinear) {
82 if (!m_toLinear)
83 m_toLinear.reset(p: new ushort[Resolution + 1]);
84 for (int i = 0; i <= Resolution; ++i) {
85 const int val = qRound(f: fun.apply(x: i * iRes) * (255 * 256));
86 if (val > 65280 && i < m_unclampedToLinear)
87 m_unclampedToLinear = i;
88 m_toLinear[i] = qBound(min: 0, val, max: 65280);
89 }
90 }
91
92 if (dir & FromLinear) {
93 if (!m_fromLinear)
94 m_fromLinear.reset(p: new ushort[Resolution + 1]);
95 for (int i = 0; i <= Resolution; ++i)
96 m_fromLinear[i] = ushort(qRound(f: qBound(min: 0.f, val: fun.applyInverse(x: i * iRes), max: 1.f) * (255 * 256)));
97 }
98}
99
100void QColorTrcLut::setFromTransferTable(const QColorTransferTable &table, Direction dir)
101{
102 constexpr float iRes = 1.f / float(Resolution);
103 if (dir & ToLinear) {
104 if (!m_toLinear)
105 m_toLinear.reset(p: new ushort[Resolution + 1]);
106 for (int i = 0; i <= Resolution; ++i)
107 m_toLinear[i] = ushort(qRound(f: table.apply(x: i * iRes) * (255 * 256)));
108 }
109
110 if (dir & FromLinear) {
111 if (!m_fromLinear)
112 m_fromLinear.reset(p: new ushort[Resolution + 1]);
113 float minInverse = 0.0f;
114 for (int i = 0; i <= Resolution; ++i) {
115 minInverse = table.applyInverse(x: i * iRes, resultLargerThan: minInverse);
116 m_fromLinear[i] = ushort(qRound(f: minInverse * (255 * 256)));
117 }
118 }
119}
120
121void QColorTrcLut::setFromTrc(const QColorTrc &trc, Direction dir)
122{
123 switch (trc.m_type) {
124 case QColorTrc::Type::ParameterizedFunction:
125 return setFromTransferFunction(fun: trc.fun(), dir);
126 case QColorTrc::Type::Table:
127 return setFromTransferTable(table: trc.table(), dir);
128 case QColorTrc::Type::GenericFunction:
129 return setFromTransferGenericFunction(fun: trc.hdr(), dir);
130 case QColorTrc::Type::Uninitialized:
131 break;
132 }
133}
134
135QT_END_NAMESPACE
136

Provided by KDAB

Privacy Policy
Learn Advanced QML with KDAB
Find out more

source code of qtbase/src/gui/painting/qcolortrclut.cpp