24#ifndef DT_PIXEL_CHROMATIC_ADAPTATION_H
25#define DT_PIXEL_CHROMATIC_ADAPTATION_H
47 { -0.7502f, 1.7135f, 0.0367f, 0.f },
48 { 0.0389f, -0.0685f, 1.0296f, 0.f } };
51 { 0.4323f, 0.5184f, 0.0493f, 0.f },
52 { -0.0085f, 0.0400f, 0.9685f, 0.f } };
55 { 0.2664f, 1.7135f, -0.0685f, 0.f },
56 { -0.1614f, 0.0367f, 1.0296f, 0.f } };
59 { -0.1471f, 0.5184f, 0.0400f, 0.f },
60 { 0.1600f, 0.0493f, 0.9685f, 0.f } };
66 return dt_mat3x4_mul_vec4(
XYZ,
72static inline __attribute__((always_inline)) dt_aligned_pixel_simd_t
76 return dt_mat3x4_mul_vec4(
LMS,
87 { -0.250268f, 1.204414f, 0.045854f, 0.f },
88 { -0.002079f, 0.048952f, 0.953127f, 0.f } };
91 { 0.38752f , 0.621447f, -0.008974f, 0.f },
92 { -0.015841f, -0.034123f, 1.049964f, 0.f } };
95 { 0.650173f, 1.204414f, 0.048952f, 0.f },
96 { -0.051461f, 0.045854f, 0.953127f, 0.f } };
99 { -1.011255f, 0.621447f, -0.034123f, 0.f },
100 { 0.149187f, -0.008974f, 1.049964f, 0.f } };
102static inline __attribute__((always_inline)) dt_aligned_pixel_simd_t
106 return dt_mat3x4_mul_vec4(
XYZ,
112static inline __attribute__((always_inline)) dt_aligned_pixel_simd_t
116 return dt_mat3x4_mul_vec4(
LMS,
123static inline __attribute__((always_inline)) dt_aligned_pixel_simd_t
142static inline __attribute__((always_inline)) dt_aligned_pixel_simd_t
170 dt_XYZ_to_Rec709_D65(
XYZ,
RGB);
173 float max_RGB = fmaxf(fmaxf(
RGB[0],
RGB[1]),
RGB[2]);
174 for(
int c = 0;
c < 3;
c++)
RGB[c] = fmaxf(
RGB[c] / max_RGB, 0.f);
181static inline __attribute__((always_inline)) dt_aligned_pixel_simd_t
182bradford_adapt_D65(
const dt_aligned_pixel_simd_t lms_in,
183 const dt_aligned_pixel_simd_t origin_illuminant,
184 const float p,
const int full)
186 static const dt_aligned_pixel_simd_t D65 = { 0.941238f, 1.040633f, 1.088932f, 0.f };
187 dt_aligned_pixel_simd_t temp = lms_in / origin_illuminant;
188 if(full) temp[2] = (temp[2] > 0.f) ? powf(temp[2],
p) : temp[2];
193static inline __attribute__((always_inline)) dt_aligned_pixel_simd_t
195 const dt_aligned_pixel_simd_t origin_illuminant,
196 const float p,
const int full)
198 static const dt_aligned_pixel_simd_t D50 = { 0.996078f, 1.020646f, 0.818155f, 0.f };
199 dt_aligned_pixel_simd_t temp = lms_in / origin_illuminant;
200 if(full) temp[2] = (temp[2] > 0.f) ? powf(temp[2],
p) : temp[2];
207static inline __attribute__((always_inline)) dt_aligned_pixel_simd_t
208CAT16_adapt_D65(
const dt_aligned_pixel_simd_t lms_in,
209 const dt_aligned_pixel_simd_t origin_illuminant,
210 const float D,
const int full)
212 static const dt_aligned_pixel_simd_t D65 = { 0.97553267f, 1.01647859f, 1.0848344f, 0.f };
213 return full ? lms_in * D65 / origin_illuminant
218static inline __attribute__((always_inline)) dt_aligned_pixel_simd_t
220 const dt_aligned_pixel_simd_t origin_illuminant,
221 const float D,
const int full)
223 static const dt_aligned_pixel_simd_t D50 = { 0.994535f, 1.000997f, 0.833036f, 0.f };
224 return full ? lms_in * D50 / origin_illuminant
230static inline __attribute__((always_inline)) dt_aligned_pixel_simd_t
231XYZ_adapt_D65(
const dt_aligned_pixel_simd_t lms_in,
232 const dt_aligned_pixel_simd_t origin_illuminant)
234 static const dt_aligned_pixel_simd_t D65 = { 0.9504285453771807f, 1.0f, 1.0889003707981277f, 0.f };
235 return lms_in * D65 / origin_illuminant;
238static inline __attribute__((always_inline)) dt_aligned_pixel_simd_t
240 const dt_aligned_pixel_simd_t origin_illuminant)
242 static const dt_aligned_pixel_simd_t D50 = { 0.9642119944211994f, 1.0f, 0.8251882845188288f, 0.f };
243 return lms_in * D50 / origin_illuminant;
249 = { { 9.89466254e-01f, -4.00304626e-02f, 4.40530317e-02f, 0.f },
250 { -5.40518733e-03f, 1.00666069e+00f, -1.75551955e-03f, 0.f },
251 { -4.03920992e-04f, 1.50768030e-02f, 1.30210211e+00f, 0.f } };
254 = { { 0.95547342f, -0.02309845f, 0.06325924f, 0.f },
255 { -0.02836971f, 1.00999540f, 0.02104144f, 0.f },
256 { 0.01231401f, -0.02050765f, 1.33036593f, 0.f } };
259 = { { 1.01085433e+00f, 4.07086103e-02f, -3.41445825e-02f, 0.f },
260 { 5.42814201e-03f, 9.93581926e-01f, 1.15592039e-03f, 0.f },
261 { 2.50722468e-04f, -1.14918759e-02f, 7.67964947e-01f, 0.f } };
264 = { { 1.04792979f, 0.02294687f, -0.05019227f, 0.f },
265 { 0.02962781f, 0.99043443f, -0.0170738f, 0.f },
266 { -0.00924304f, 0.01505519f, 0.75187428f, 0.f } };
269 = { { 9.89466254e-01f, -5.40518733e-03f, -4.03920992e-04f, 0.f },
270 { -4.00304626e-02f, 1.00666069e+00f, 1.50768030e-02f, 0.f },
271 { 4.40530317e-02f, -1.75551955e-03f, 1.30210211e+00f, 0.f } };
274 = { { 1.01085433e+00f, 5.42814201e-03f, 2.50722468e-04f, 0.f },
275 { 4.07086103e-02f, 9.93581926e-01f, -1.14918759e-02f, 0.f },
276 { -3.41445825e-02f, 1.15592039e-03f, 7.67964947e-01f, 0.f } };
292static inline __attribute__((always_inline)) dt_aligned_pixel_simd_t
293_downscale_vector_simd(
const dt_aligned_pixel_simd_t vector,
const float scaling)
299static inline __attribute__((always_inline)) dt_aligned_pixel_simd_t
300_upscale_vector_simd(
const dt_aligned_pixel_simd_t vector,
const float scaling)
306static inline __attribute__((always_inline)) dt_aligned_pixel_simd_t
307chroma_adapt_pixel(
const dt_aligned_pixel_simd_t in,
313 const float Y = in[1];
362 dt_store_simd_aligned(D50, (dt_aligned_pixel_simd_t){ 0.9642119944211994f, 1.0f, 0.8251882845188288f, 0.f });
typedef void((*dt_cache_allocate_t)(void *userdata, dt_cache_entry_t *entry))
static void XYZ_D50_to_D65(const dt_aligned_pixel_t XYZ_in, dt_aligned_pixel_t XYZ_out)
static const dt_aligned_pixel_simd_t const dt_adaptation_t adaptation
static const dt_colormatrix_t XYZ_D50_to_D65_Bradford
static const dt_colormatrix_t CAT16_LMS_to_XYZ
static void XYZ_D65_to_D50(const dt_aligned_pixel_t XYZ_in, dt_aligned_pixel_t XYZ_out)
static const dt_adaptation_t kind
static const dt_colormatrix_t XYZ_D65_to_D50_CAT16
static const dt_colormatrix_t XYZ_to_CAT16_LMS
static void convert_D50_to_LMS(const dt_adaptation_t adaptation, dt_aligned_pixel_t D50)
static const dt_colormatrix_t XYZ_to_CAT16_LMS_transposed
@ DT_ADAPTATION_FULL_BRADFORD
@ DT_ADAPTATION_LINEAR_BRADFORD
static const dt_colormatrix_t XYZ_to_Bradford_LMS_transposed
static const dt_colormatrix_t XYZ_D65_to_D50_CAT16_transposed
static const dt_colormatrix_t XYZ_D50_to_D65_CAT16_transposed
static const dt_aligned_pixel_simd_t const dt_adaptation_t const float p
static const dt_colormatrix_t XYZ_to_Bradford_LMS
static const dt_colormatrix_t Bradford_LMS_to_XYZ
static const float scaling
static const dt_colormatrix_t CAT16_LMS_to_XYZ_transposed
static const dt_colormatrix_t XYZ_D65_to_D50_Bradford
static const dt_colormatrix_t Bradford_LMS_to_XYZ_transposed
return vector dt_simd_set1(valid ?(scaling+NORM_MIN) :NORM_MIN)
static const dt_aligned_pixel_simd_t illuminant
static void CAT16_adapt_D50(float4 *lms_in, const float4 origin_illuminant, const float D, const int full)
static float4 convert_XYZ_to_bradford_LMS(const float4 XYZ)
static float4 convert_XYZ_to_CAT16_LMS(const float4 XYZ)
static void bradford_adapt_D50(float4 *lms_in, const float4 origin_illuminant, const float p, const int full)
static void XYZ_adapt_D50(float4 *lms_in, const float4 origin_illuminant)
static float4 convert_CAT16_LMS_to_XYZ(const float4 LMS)
static float4 convert_bradford_LMS_to_XYZ(const float4 LMS)
dt_apply_transposed_color_matrix(XYZ, xyz_to_srgb_matrix_transposed, sRGB)
static dt_aligned_pixel_t XYZ
dt_store_simd_aligned(out, dt_mat3x4_mul_vec4(vin, dt_colormatrix_row_to_simd(matrix, 0), dt_colormatrix_row_to_simd(matrix, 1), dt_colormatrix_row_to_simd(matrix, 2)))
static dt_aligned_pixel_t RGB
float DT_ALIGNED_ARRAY dt_colormatrix_t[4][4]
#define __OMP_DECLARE_SIMD__(...)
DT_ALIGNED_PIXEL float dt_aligned_pixel_t[4]
float dt_aligned_pixel_simd_t __attribute__((vector_size(16), aligned(16)))
Apply one channel's tone curve to each of the three colour channels, or pass the channel through unto...