OrcaSlicer latest
OrcaSlicer
Loading...
Searching...
No Matches
FlushPredict Namespace Reference

Classes

struct  RGBColor
struct  LABColor

Functions

static double rad_to_deg (double rad)
static double deg_to_rad (double deg)
LABColor RGB2LAB (const RGBColor &color)
float calc_color_distance (const LABColor &lab1, const LABColor &lab2)
float calc_color_distance (const RGBColor &color1, const RGBColor &color2)
bool is_similar_color (const RGBColor &from, const RGBColor &to, float distance_threshold)

Function Documentation

◆ calc_color_distance() [1/2]

float FlushPredict::calc_color_distance ( const LABColor & lab1,
const LABColor & lab2 )
74 {
75 static const double pow_25_to_7 = pow(25, 7);
76
77 const double C1 = sqrt(lab1.a * lab1.a + lab1.b * lab1.b);
78 const double C2 = sqrt(lab2.a * lab2.a + lab2.b * lab2.b);
79 const double CMean = (C1 + C2) / 2.0;
80 const double pow_CMean_to_7 = pow(CMean, 7);
81 const double G = 0.5 * (1 - sqrt(pow_CMean_to_7 / (pow_CMean_to_7 + pow_25_to_7)));
82
83 const double p_l1 = lab1.l;
84 const double p_l2 = lab2.l;
85 const double p_a1 = (1. + G) * lab1.a;
86 const double p_a2 = (1. + G) * lab2.a;
87 const double p_b1 = lab1.b;
88 const double p_b2 = lab2.b;
89 const double p_c1 = sqrt(p_a1 * p_a1 + p_b1 * p_b1);
90 const double p_c2 = sqrt(p_a2 * p_a2 + p_b2 * p_b2);
91 double p_h1;
92 if (p_a1 == 0 && p_b1 == 0)
93 p_h1 = 0;
94 else {
95 p_h1 = atan2(p_b1, p_a1);
96 if (p_h1 < 0)
97 p_h1 += M_PI * 2;
98 }
99 double p_h2;
100 if (p_a2 == 0 && p_b2 == 0)
101 p_h2 = 0;
102 else {
103 p_h2 = atan2(p_b2, p_a2);
104 if (p_h2 < 0)
105 p_h2 += M_PI * 2;
106 }
107
108 const double delta_L = p_l2 - p_l1;
109 const double delta_C = p_c2 - p_c1;
110
111 double delta_H;
112 const double p_c_multi = p_c1 * p_c2;
113 if (p_c_multi == 0)
114 delta_H = 0;
115 else {
116 delta_H = p_h2 - p_h1;
117 if (delta_H < -M_PI)
118 delta_H += 2 * M_PI;
119 else if (delta_H > M_PI)
120 delta_H -= 2 * M_PI;
121 delta_H = 2 * sqrt(p_c_multi) * sin(delta_H / 2.);
122 }
123
124
125 double p_L_mean = (p_l1 + p_l2) / 2.0;
126 double p_C_mean = (p_c1 + p_c2) / 2.0;
127
128 double p_H_mean, p_H_sum = p_h1 + p_h2;
129 if (p_c1 * p_c2 == 0) {
130 p_H_mean = p_H_sum;
131 }
132 else {
133 if (fabs(p_h1 - p_h2) <= M_PI)
134 p_H_mean = p_H_sum / 2;
135 else {
136 if (p_H_sum < 2 * M_PI)
137 p_H_mean = (p_H_sum + 2 * M_PI) / 2.0;
138 else
139 p_H_mean = (p_H_sum - 2 * M_PI) / 2.0;
140 }
141 }
142
143 const double T = 1 - 0.17 * cos(p_H_mean - deg_to_rad(30)) + 0.24 * cos(2 * p_H_mean) + 0.32 * cos(3 * p_H_mean + deg_to_rad(6)) - 0.2 * cos(4 * p_H_mean - deg_to_rad(63));
144 const double dtheta = deg_to_rad(30) * exp(-pow((p_H_mean - deg_to_rad(275)) / deg_to_rad(25), 2));
145
146 const double pow_p_cmean_to_7 = pow(p_C_mean, 7);
147 const double R_C = 2 * sqrt(pow_p_cmean_to_7 / (pow_p_cmean_to_7 + pow_25_to_7));
148
149 const double pow_p_lmean_to_2 = pow(p_L_mean - 50, 2);
150 const double S_L = 1 + (0.015 * pow_p_lmean_to_2) / sqrt(20 + pow_p_lmean_to_2);
151 const double S_C = 1 + 0.045 * p_C_mean;
152 const double S_H = 1 + 0.015 * p_C_mean * T;
153 const double R_T = -sin(2 * dtheta) * R_C;
154
155 const double K_L = 1.0, K_C = 1.0, K_H = 1.0;
156
157 double de = sqrt(
158 pow(delta_L / (K_L * S_L), 2) + pow(delta_C / (K_C * S_C), 2) + pow(delta_H / (K_H * S_H), 2) + (R_T * (delta_C / (K_C * S_C)) * (delta_H / (K_H * S_H)))
159 );
160 return de;
161 }
#define M_PI
Definition ExtrusionSimulator.cpp:31
static double deg_to_rad(double deg)
Definition FlushVolPredictor.cpp:24
double b
Definition FlushVolPredictor.hpp:24
double a
Definition FlushVolPredictor.hpp:23
double l
Definition FlushVolPredictor.hpp:22

References FlushPredict::LABColor::a, FlushPredict::LABColor::b, deg_to_rad(), FlushPredict::LABColor::l, and M_PI.

Referenced by calc_color_distance(), Slic3r::FilamentGroup::calc_filament_group_for_match(), is_similar_color(), and Slic3r::select_best_group_for_ams().

Here is the call graph for this function:
Here is the caller graph for this function:

◆ calc_color_distance() [2/2]

float FlushPredict::calc_color_distance ( const RGBColor & color1,
const RGBColor & color2 )
163 {
164 LABColor lab1 = RGB2LAB(color1);
165 LABColor lab2 = RGB2LAB(color2);
166 return calc_color_distance(lab1, lab2);
167 }
float calc_color_distance(const LABColor &lab1, const LABColor &lab2)
Definition FlushVolPredictor.cpp:73
LABColor RGB2LAB(const RGBColor &color)
Definition FlushVolPredictor.cpp:28
Definition FlushVolPredictor.hpp:21

References calc_color_distance(), and RGB2LAB().

Here is the call graph for this function:

◆ deg_to_rad()

double FlushPredict::deg_to_rad ( double deg)
static
24 {
25 return deg * M_PI / 180.0;
26 }

References M_PI.

Referenced by calc_color_distance().

Here is the caller graph for this function:

◆ is_similar_color()

bool FlushPredict::is_similar_color ( const RGBColor & from,
const RGBColor & to,
float distance_threshold )
170 {
171 float color_distance = calc_color_distance(from, to);
172 if (color_distance > distance_threshold)
173 return false;
174 return true;
175 }

References calc_color_distance().

Referenced by FlushVolPredictor::predict().

Here is the call graph for this function:
Here is the caller graph for this function:

◆ rad_to_deg()

double FlushPredict::rad_to_deg ( double rad)
static
20 {
21 return 180.0 / M_PI * rad;
22 }

References M_PI.

◆ RGB2LAB()

LABColor FlushPredict::RGB2LAB ( const RGBColor & color)
28 {
29 using XYZColor = std::tuple<double, double, double>;
30 auto gamma = [](double x) {
31 if (x > 0.04045)
32 return pow((x + 0.055) / 1.055, 2.4);
33 else
34 return x / 12.92;
35 };
36 auto RGB2XYZ = [gamma](const RGBColor& color)->XYZColor {
37 double R = gamma(static_cast<double>(color.r) / 255.0) * 100;
38 double G = gamma(static_cast<double>(color.g) / 255.0) * 100;
39 double B = gamma(static_cast<double>(color.b) / 255.0) * 100;
40
41 double x = 0.412453 * R + 0.357580 * G + 0.180423 * B;
42 double y = 0.212671 * R + 0.715160 * G + 0.072169 * B;
43 double z = 0.019334 * R + 0.119193 * G + 0.950227 * B;
44 return { x,y,z };
45 };
46
47 static const double XN = 95.0489;
48 static const double YN = 100;
49 static const double ZN = 108.8840;
50
51 auto f = [](double t) {
52 static const double threshold = 0.008856f;
53 if (t > threshold)
54 return pow(t, 1.0 / 3.0);
55 else
56 return 7.787 * t + 0.137931;
57 };
58
59 auto xyz_color = RGB2XYZ(color);
60 double x = std::get<0>(xyz_color);
61 double y = std::get<1>(xyz_color);
62 double z = std::get<2>(xyz_color);
63 double xn = f(x / XN);
64 double yn = f(y / YN);
65 double zn = f(z / ZN);
66
67 double L = 116.0 * yn - 16.0;
68 double A = 500.0 * (xn - yn);
69 double B = 200.0 * (yn - zn);
70 return LABColor(L, A, B);
71 }
void RGB2XYZ(float R, float G, float B, float *X, float *Y, float *Z)
Definition ColorSpaceConvert.cpp:85
#define L(s)
Definition ExtrusionEntity.cpp:25
unsigned char b
Definition FlushVolPredictor.hpp:15
unsigned char r
Definition FlushVolPredictor.hpp:13
unsigned char g
Definition FlushVolPredictor.hpp:14

References FlushPredict::RGBColor::b, FlushPredict::RGBColor::g, L, FlushPredict::RGBColor::r, and RGB2XYZ().

Referenced by calc_color_distance().

Here is the call graph for this function:
Here is the caller graph for this function: