diff --git a/rtengine/iimage.h b/rtengine/iimage.h index 4362f369a..cd49c1329 100644 --- a/rtengine/iimage.h +++ b/rtengine/iimage.h @@ -103,7 +103,7 @@ public: template<> inline void ImageDatas::convertTo(unsigned short src, unsigned char& dst) const { - dst = (src + 128) / 257; + dst = uint16ToUint8Rounded(src); } template<> inline void ImageDatas::convertTo(unsigned char src, int& dst) const @@ -118,7 +118,7 @@ inline void ImageDatas::convertTo(unsigned char src, unsigned short& dst) const template<> inline void ImageDatas::convertTo(float src, unsigned char& dst) const { - dst = (static_cast(src) + 128) / 257; + dst = uint16ToUint8Rounded(src); } template<> inline void ImageDatas::convertTo(unsigned char src, float& dst) const diff --git a/rtengine/image16.cc b/rtengine/image16.cc index 11a05902f..b61170e03 100644 --- a/rtengine/image16.cc +++ b/rtengine/image16.cc @@ -28,9 +28,9 @@ namespace void getScanline8 (const uint16_t *red, const uint16_t *green, const uint16_t *blue, int width, unsigned char* buffer) { for (int i = 0, ix = 0; i < width; i++) { - buffer[ix++] = (red[i] + 128) / 257; - buffer[ix++] = (green[i] + 128) / 257; - buffer[ix++] = (blue[i] + 128) / 257; + buffer[ix++] = rtengine::uint16ToUint8Rounded(red[i]); + buffer[ix++] = rtengine::uint16ToUint8Rounded(green[i]); + buffer[ix++] = rtengine::uint16ToUint8Rounded(blue[i]); } } @@ -300,9 +300,9 @@ Image16::to8() for (int h = 0; h < height; ++h) { for (int w = 0; w < width; ++w) { - img8->r(h, w) = (r(h, w) + 128) / 257; - img8->g(h, w) = (g(h, w) + 128) / 257; - img8->b(h, w) = (b(h, w) + 128) / 257; + img8->r(h, w) = uint16ToUint8Rounded(r(h, w)); + img8->g(h, w) = uint16ToUint8Rounded(g(h, w)); + img8->b(h, w) = uint16ToUint8Rounded(b(h, w)); } } diff --git a/rtengine/image8.cc b/rtengine/image8.cc index 41589993d..d7a49138b 100644 --- a/rtengine/image8.cc +++ b/rtengine/image8.cc @@ -74,7 +74,7 @@ void Image8::setScanline (int row, unsigned char* buffer, int bps, float *minVal unsigned short* sbuffer = (unsigned short*) buffer; for (int i = 0, ix = row * width * 3; i < width * 3; ++i, ++ix) { - data[ix] = (sbuffer[i] + 128) / 257; + data[ix] = uint16ToUint8Rounded(sbuffer[i]); } break; diff --git a/rtengine/imagefloat.cc b/rtengine/imagefloat.cc index 7f84f1cab..ae4a1a09b 100644 --- a/rtengine/imagefloat.cc +++ b/rtengine/imagefloat.cc @@ -335,9 +335,9 @@ Imagefloat::to8() for (int h = 0; h < height; ++h) { for (int w = 0; w < width; ++w) { - img8->r(h, w) = (static_cast(r(h, w)) + 128) / 257; - img8->g(h, w) = (static_cast(g(h, w)) + 128) / 257; - img8->b(h, w) = (static_cast(b(h, w)) + 128) / 257; + img8->r(h, w) = uint16ToUint8Rounded(r(h, w)); + img8->g(h, w) = uint16ToUint8Rounded(g(h, w)); + img8->b(h, w) = uint16ToUint8Rounded(b(h, w)); } } diff --git a/rtengine/iplab2rgb.cc b/rtengine/iplab2rgb.cc index 419854523..8aff50886 100644 --- a/rtengine/iplab2rgb.cc +++ b/rtengine/iplab2rgb.cc @@ -107,9 +107,9 @@ void ImProcFunctions::lab2monitorRgb (LabImage* lab, Image8* image) /* copy RGB */ //int R1=((int)gamma2curve[(R)]) - data[ix++] = (static_cast(Color::gamma2curve[R]) + 128) / 257; - data[ix++] = (static_cast(Color::gamma2curve[G]) + 128) / 257; - data[ix++] = (static_cast(Color::gamma2curve[B]) + 128) / 257; + data[ix++] = uint16ToUint8Rounded(Color::gamma2curve[R]); + data[ix++] = uint16ToUint8Rounded(Color::gamma2curve[G]); + data[ix++] = uint16ToUint8Rounded(Color::gamma2curve[B]); } } } @@ -218,9 +218,9 @@ Image8* ImProcFunctions::lab2rgb (LabImage* lab, int cx, int cy, int cw, int ch, Color::xyz2rgb(x_, y_, z_, R, G, B, xyz_rgb); - image->data[ix++] = (static_cast(Color::gamma2curve[R]) + 128) / 257; - image->data[ix++] = (static_cast(Color::gamma2curve[G]) + 128) / 257; - image->data[ix++] = (static_cast(Color::gamma2curve[B]) + 128) / 257; + image->data[ix++] = uint16ToUint8Rounded(Color::gamma2curve[R]); + image->data[ix++] = uint16ToUint8Rounded(Color::gamma2curve[G]); + image->data[ix++] = uint16ToUint8Rounded(Color::gamma2curve[B]); } } } diff --git a/rtengine/rt_math.h b/rtengine/rt_math.h index f55f7c1b2..67d883080 100644 --- a/rtengine/rt_math.h +++ b/rtengine/rt_math.h @@ -1,14 +1,15 @@ -#ifndef _MYMATH_ -#define _MYMATH_ -#include -#include +#pragma once +#include +#include +#include namespace rtengine { -static const int MAXVAL = 0xffff; -static const float MAXVALF = float(MAXVAL); // float version of MAXVAL -static const double MAXVALD = double(MAXVAL); // double version of MAXVAL + +constexpr int MAXVAL = 0xffff; +constexpr float MAXVALF = static_cast(MAXVAL); // float version of MAXVAL +constexpr double MAXVALD = static_cast(MAXVAL); // double version of MAXVAL template inline _Tp SQR (_Tp x) @@ -107,6 +108,9 @@ inline int float2uint16range(float d) // clips input to [0;65535] and rounds return d + 0.5f; } +constexpr std::uint8_t uint16ToUint8Rounded(std::uint16_t i) +{ + return ((i + 128) - ((i + 128) >> 8)) >> 8; } -#endif +}