10#if XSIMD_UNIVERSAL_BUILD_PASS
14#if !defined(XSIMD_NO_SUPPORTED_ARCHITECTURE)
15template<
typename Arch,
18 typename std::enable_if_t<!std::is_same<Arch, xsimd::generic>::value,
20inline void linearize(
float *pixelValues,
27 auto v = float_v::load_unaligned(pixelValues);
29 v.store_unaligned(pixelValues);
31 auto v = float_v::load_unaligned(pixelValues);
33 v.store_unaligned(pixelValues);
35 auto v = float_v::load_unaligned(pixelValues);
37 v.store_unaligned(pixelValues);
41 qSwap(pixelValues[0], pixelValues[2]);
43 applyHLGOOTF(pixelValues, lCoef, displayGamma, displayNits);
48template<
typename Arch,
51 typename std::enable_if_t<std::is_same<Arch, xsimd::generic>::value,
53inline void linearize(
float *pixelValues,
59 qSwap(pixelValues[0], pixelValues[2]);
61 applyHLGOOTF(pixelValues, lCoef, displayGamma, displayNits);
65template<
typename Arch,
68 typename std::enable_if_t<!std::is_same<Arch, xsimd::generic>::value,
70inline float value(
const uint8_t *img,
int stride,
int x,
int y)
73 return float(img[y * (stride) + x]) / 255.0f;
76 reinterpret_cast<const uint16_t *
>(img)[y * (stride / 2) +
x];
79 }
else if (luma == 12) {
87template<LinearizePolicy policy>
100template<
typename Arch,
103 typename std::enable_if_t<std::is_same<Arch, xsimd::generic>::value,
105inline float value(
const uint8_t *img,
int stride,
int x,
int y)
108 return linearizeValueAsNeeded<linearizePolicy>(
109 float(img[y * (stride) + x]) / 255.0f);
112 reinterpret_cast<const uint16_t *
>(img)[y * (stride / 2) +
x];
114 return linearizeValueAsNeeded<linearizePolicy>(
116 }
else if (luma == 12) {
117 return linearizeValueAsNeeded<linearizePolicy>(
120 return linearizeValueAsNeeded<linearizePolicy>(
float(
source)
126template<
typename Arch,
127 typename std::enable_if_t<std::is_same<Arch, xsimd::generic>::value,
129constexpr int bufferSize()
134#if !defined(XSIMD_NO_SUPPORTED_ARCHITECTURE)
135template<
typename Arch,
136 typename std::enable_if_t<!std::is_same<Arch, xsimd::generic>::value,
138constexpr int bufferSize()
144template<
typename Arch,
166 float *data = pixelValues.data();
168 for (
int y = 0;
y < height;
y++) {
169 for (
int x = 0;
x < width;
x++) {
170 for (
int i = 0; i < bufferSize<Arch>(); i++) {
174 data[0] = value<Arch, luma, linearizePolicy>(imgR, strideR, x, y);
175 data[1] = value<Arch, luma, linearizePolicy>(imgG, strideG, x, y);
176 data[2] = value<Arch, luma, linearizePolicy>(imgB, strideB, x, y);
178 linearize<Arch, linearizePolicy, applyOOTF>(data,
185 value<Arch, luma, LinearizePolicy::KeepTheSame>(imgA,
209template<
typename Arch,
214inline auto readPlanarLayerWithAlpha(
bool hasAlpha, Args &&...args)
217 return Planar::readLayer<Arch, luma, linearizePolicy, applyOOTF, true>(
218 std::forward<Args>(args)...);
220 return Planar::readLayer<Arch, luma, linearizePolicy, applyOOTF, false>(
221 std::forward<Args>(args)...);
225template<
typename Arch,
229inline auto readPlanarLayerWithPolicy(
bool applyOOTF, Args &&...args)
232 return readPlanarLayerWithAlpha<Arch, luma, linearizePolicy, true>(
233 std::forward<Args>(args)...);
235 return readPlanarLayerWithAlpha<Arch, luma, linearizePolicy, false>(
236 std::forward<Args>(args)...);
240template<
typename Arch,
int luma,
typename... Args>
245 return readPlanarLayerWithPolicy<Arch, luma, LinearizePolicy::LinearFromHLG>(std::forward<Args>(args)...);
247 return readPlanarLayerWithPolicy<Arch, luma, LinearizePolicy::LinearFromPQ>(std::forward<Args>(args)...);
249 return readPlanarLayerWithPolicy<Arch, luma, LinearizePolicy::LinearFromSMPTE428>(std::forward<Args>(args)...);
251 return readPlanarLayerWithPolicy<Arch, luma, LinearizePolicy::KeepTheSame>(std::forward<Args>(args)...);
255template<
typename Arch>
276 return readPlanarLayerWithLuma<xsimd::current_arch, 8>(policy,
293 }
else if (luma == 10) {
294 return readPlanarLayerWithLuma<xsimd::current_arch, 10>(policy,
311 }
else if (luma == 12) {
312 return readPlanarLayerWithLuma<xsimd::current_arch, 12>(policy,
330 return readPlanarLayerWithLuma<xsimd::current_arch, 16>(policy,
351readLayerImpl::create<xsimd::current_arch>(
const int luma,
374#if !defined(XSIMD_NO_SUPPORTED_ARCHITECTURE)
375template<
typename Arch,
378 typename std::enable_if_t<!std::is_same<Arch, xsimd::generic>::value,
380inline void linearize(
float *pixelValues,
387 auto v = float_v::load_unaligned(pixelValues);
389 v.store_unaligned(pixelValues);
391 auto v = float_v::load_unaligned(pixelValues);
393 v.store_unaligned(pixelValues);
395 auto v = float_v::load_unaligned(pixelValues);
397 v.store_unaligned(pixelValues);
401 qSwap(pixelValues[0], pixelValues[2]);
403 applyHLGOOTF(pixelValues, lCoef, displayGamma, displayNits);
408template<
typename Arch,
411 typename std::enable_if_t<std::is_same<Arch, xsimd::generic>::value,
413inline void linearize(
float *pixelValues,
419 qSwap(pixelValues[0], pixelValues[2]);
421 applyHLGOOTF(pixelValues, lCoef, displayGamma, displayNits);
425template<
typename Arch,
428 typename std::enable_if_t<!std::is_same<Arch, xsimd::generic>::value,
430inline float valueInterleaved(
const uint8_t *img,
437 uint16_t
source =
reinterpret_cast<const uint16_t *
>(
438 img)[y * (stride / 2) + (
x * channels) + ch];
441 }
else if (luma == 12) {
448template<LinearizePolicy policy>
461template<
typename Arch,
464 typename std::enable_if_t<std::is_same<Arch, xsimd::generic>::value,
466inline float valueInterleaved(
const uint8_t *img,
473 uint16_t
source =
reinterpret_cast<const uint16_t *
>(
474 img)[y * (stride / 2) + (
x * channels) + ch];
476 return linearizeValueAsNeeded<linearizePolicy>(
float(0x03ff & (
source))
478 }
else if (luma == 12) {
479 return linearizeValueAsNeeded<linearizePolicy>(
float(0x0fff & (
source))
482 return linearizeValueAsNeeded<linearizePolicy>(
float(
source)
487template<
typename Arch,
489 typename std::enable_if_t<std::is_same<Arch, xsimd::generic>::value,
491constexpr int bufferSize()
496#if !defined(XSIMD_NO_SUPPORTED_ARCHITECTURE)
497template<
typename Arch,
499 typename std::enable_if_t<!std::is_same<Arch, xsimd::generic>::value,
501constexpr int bufferSize()
507template<
typename Arch,
523 float *data = pixelValues.data();
525 for (
int y = 0;
y < height;
y++) {
526 for (
int x = 0;
x < width;
x++) {
527 for (
int i = 0; i < bufferSize<Arch, channels>(); i++) {
531 const int alphaPos = [&]() {
542 for (
int ch = 0; ch < channels; ch++) {
543 if (ch == alphaPos) {
545 valueInterleaved<Arch,
555 valueInterleaved<Arch, luma, linearizePolicy>(img,
564 linearize<Arch, linearizePolicy, applyOOTF>(data,
587template<
typename Arch,
592inline auto readInterleavedWithAlpha(
bool hasAlpha, Args &&...args)
595 return HDR::readLayer<Arch, luma, linearizePolicy, applyOOTF, 4>(
596 std::forward<Args>(args)...);
598 return HDR::readLayer<Arch, luma, linearizePolicy, applyOOTF, 3>(
599 std::forward<Args>(args)...);
603template<
typename Arch,
607inline auto readInterleavedWithPolicy(
bool applyOOTF, Args &&...args)
610 return readInterleavedWithAlpha<Arch, luma, linearizePolicy, true>(
611 std::forward<Args>(args)...);
613 return readInterleavedWithAlpha<Arch, luma, linearizePolicy, false>(
614 std::forward<Args>(args)...);
618template<
typename Arch,
int luma,
typename... Args>
623 return readInterleavedWithPolicy<Arch, luma, LinearizePolicy::LinearFromHLG>(std::forward<Args>(args)...);
625 return readInterleavedWithPolicy<Arch, luma, LinearizePolicy::LinearFromPQ>(std::forward<Args>(args)...);
627 return readInterleavedWithPolicy<Arch, luma, LinearizePolicy::LinearFromSMPTE428>(std::forward<Args>(args)...);
629 return readInterleavedWithPolicy<Arch, luma, LinearizePolicy::KeepTheSame>(std::forward<Args>(args)...);
633template<
typename Arch>
634void readLayerImpl::create(
const int luma,
648 return readInterleavedWithLuma<Arch, 10>(linearizePolicy,
659 }
else if (luma == 12) {
660 return readInterleavedWithLuma<Arch, 12>(linearizePolicy,
672 return readInterleavedWithLuma<Arch, 16>(linearizePolicy,
687readLayerImpl::create<xsimd::current_arch>(
const int luma,
703#if !defined(XSIMD_NO_SUPPORTED_ARCHITECTURE)
704template<
typename Arch,
707 typename std::enable_if_t<!std::is_same<Arch, xsimd::generic>::value,
709inline void linearize(
float *pixelValues,
716 auto v = float_v::load_unaligned(pixelValues);
718 v.store_unaligned(pixelValues);
720 auto v = float_v::load_unaligned(pixelValues);
722 v.store_unaligned(pixelValues);
724 auto v = float_v::load_unaligned(pixelValues);
726 v.store_unaligned(pixelValues);
730 qSwap(pixelValues[0], pixelValues[2]);
732 applyHLGOOTF(pixelValues, lCoef, displayGamma, displayNits);
737template<
typename Arch,
740 typename std::enable_if_t<std::is_same<Arch, xsimd::generic>::value,
742inline void linearize(
float *pixelValues,
748 qSwap(pixelValues[0], pixelValues[2]);
750 applyHLGOOTF(pixelValues, lCoef, displayGamma, displayNits);
754template<
typename Arch,
757 typename std::enable_if_t<!std::is_same<Arch, xsimd::generic>::value,
759inline float value(
const uint8_t *img,
int stride,
int x,
int y,
int ch)
761 uint8_t
source = img[(
y * stride) + (x * channels) + ch];
762 return float(
source) / 255.0f;
765template<LinearizePolicy policy>
778template<
typename Arch,
781 typename std::enable_if_t<std::is_same<Arch, xsimd::generic>::value,
783inline float value(
const uint8_t *img,
int stride,
int x,
int y,
int ch)
785 uint8_t
source = img[(
y * stride) + (x * channels) + ch];
786 return linearizeValueAsNeeded<linearizePolicy>(
float(
source) / 255.0f);
789template<
typename Arch,
791 typename std::enable_if_t<std::is_same<Arch, xsimd::generic>::value,
793constexpr int bufferSize()
798#if !defined(XSIMD_NO_SUPPORTED_ARCHITECTURE)
799template<
typename Arch,
801 typename std::enable_if_t<!std::is_same<Arch, xsimd::generic>::value,
803constexpr int bufferSize()
809template<
typename Arch,
824 float *data = pixelValues.data();
826 for (
int y = 0;
y < height;
y++) {
827 for (
int x = 0;
x < width;
x++) {
828 for (
int i = 0; i < bufferSize<Arch, channels>(); i++) {
832 for (
int ch = 0; ch < channels; ch++) {
835 value<Arch, LinearizePolicy::KeepTheSame, channels>(
842 data[ch] = value<Arch, linearizePolicy, channels>(img,
850 linearize<Arch, linearizePolicy, applyOOTF>(data,
865template<
typename Arch,
869inline auto readInterleavedWithAlpha(
bool hasAlpha, Args &&...args)
872 return SDR::readLayer<Arch, linearizePolicy, applyOOTF, 4>(
873 std::forward<Args>(args)...);
875 return SDR::readLayer<Arch, linearizePolicy, applyOOTF, 3>(
876 std::forward<Args>(args)...);
880template<
typename Arch,
LinearizePolicy linearizePolicy,
typename... Args>
881inline auto readInterleavedWithPolicy(
bool applyOOTF, Args &&...args)
884 return readInterleavedWithAlpha<Arch, linearizePolicy, true>(
885 std::forward<Args>(args)...);
887 return readInterleavedWithAlpha<Arch, linearizePolicy, false>(
888 std::forward<Args>(args)...);
892template<
typename Arch>
906 return readInterleavedWithPolicy<Arch, LinearizePolicy::LinearFromHLG>(applyOOTF,
917 return readInterleavedWithPolicy<Arch, LinearizePolicy::LinearFromPQ>(applyOOTF,
928 return readInterleavedWithPolicy<Arch, LinearizePolicy::LinearFromSMPTE428>(applyOOTF,
939 return readInterleavedWithPolicy<Arch, LinearizePolicy::KeepTheSame>(applyOOTF,
953readLayerImpl::create<xsimd::current_arch>(
LinearizePolicy linearizePolicy,
float value(const T *src, size_t ch)
float linearizeValueAsNeeded(float value)
KisMagneticGraph::vertex_descriptor source(typename KisMagneticGraph::edge_descriptor e, KisMagneticGraph g)
ALWAYS_INLINE void applyHLGOOTF(float *rgb, const double *lumaCoefficients, float gamma=1.2f, float nominalPeak=1000.0f) noexcept
ALWAYS_INLINE float removeHLGCurve(float x) noexcept
LinearizePolicy
The KoColorTransferFunctions class.
static constexpr float multiplier12bit
static constexpr float multiplier10bit
ALWAYS_INLINE float removeSMPTE_ST_428Curve(float x) noexcept
static constexpr float multiplier16bit
ALWAYS_INLINE float removeSmpte2048Curve(float x) noexcept
QVector< qreal > lumaCoefficients
void readLayer(const int width, const int height, KisHLineIteratorSP it, const uint8_t *imgG, const uint8_t *imgA, const int strideG, const int strideA)
static const qint32 alpha_pos
static void fromNormalisedChannelsValue(quint8 *pixel, const QVector< float > &values)
static ALWAYS_INLINE void removeSmpte2048Curve(float_v &x) noexcept
typename KoStreamedMath< Arch >::float_v float_v
static ALWAYS_INLINE void removeSMPTE_ST_428Curve(float_v &x) noexcept
static ALWAYS_INLINE void removeHLGCurve(float_v &x) noexcept
static void create(const int luma, LinearizePolicy policy, bool applyOOTF, bool hasAlpha, const int width, const int height, const uint8_t *imgR, const int strideR, const uint8_t *imgG, const int strideG, const uint8_t *imgB, const int strideB, const uint8_t *imgA, const int strideA, KisHLineIteratorSP it, float displayGamma, float displayNits, const KoColorSpace *colorSpace)