Welcome to mirror list, hosted at ThFree Co, Russian Federation.

git.blender.org/blender.git - Unnamed repository; edit this file 'description' to name the repository.
summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
-rw-r--r--release/datafiles/colormanagement/config.ocio2
-rw-r--r--source/blender/editors/interface/interface.c21
-rw-r--r--source/blender/editors/interface/interface_draw.c5
-rw-r--r--source/blender/editors/interface/interface_handlers.c46
-rw-r--r--source/blender/editors/interface/interface_intern.h9
-rw-r--r--source/blender/editors/interface/interface_region_color_picker.c134
-rw-r--r--source/blender/editors/interface/interface_widgets.c88
-rw-r--r--source/blender/imbuf/IMB_colormanagement.h3
-rw-r--r--source/blender/imbuf/intern/colormanagement.c66
9 files changed, 199 insertions, 175 deletions
diff --git a/release/datafiles/colormanagement/config.ocio b/release/datafiles/colormanagement/config.ocio
index bba5958769d..411af8ebdf2 100644
--- a/release/datafiles/colormanagement/config.ocio
+++ b/release/datafiles/colormanagement/config.ocio
@@ -34,7 +34,7 @@ roles:
default_sequencer: sRGB
# Color spaces for color picking and texture painting (not internally supported yet)
- color_picking: Raw
+ color_picking: sRGB
texture_paint: Raw
# Non-color data
diff --git a/source/blender/editors/interface/interface.c b/source/blender/editors/interface/interface.c
index 39dcdda5ee8..2a4dfc210b0 100644
--- a/source/blender/editors/interface/interface.c
+++ b/source/blender/editors/interface/interface.c
@@ -2992,19 +2992,20 @@ uiBlock *UI_block_begin(const bContext *C, ARegion *region, const char *name, sh
block->evil_C = (void *)C; /* XXX */
if (scn) {
- block->color_profile = true;
-
/* store display device name, don't lookup for transformations yet
* block could be used for non-color displays where looking up for transformation
* would slow down redraw, so only lookup for actual transform when it's indeed
* needed
*/
- BLI_strncpy(block->display_device, scn->display_settings.display_device, sizeof(block->display_device));
+ STRNCPY(block->display_device, scn->display_settings.display_device);
/* copy to avoid crash when scene gets deleted with ui still open */
block->unit = MEM_mallocN(sizeof(scn->unit), "UI UnitSettings");
memcpy(block->unit, &scn->unit, sizeof(scn->unit));
}
+ else {
+ STRNCPY(block->display_device, IMB_colormanagement_display_get_default_name());
+ }
BLI_strncpy(block->name, name, sizeof(block->name));
@@ -3295,20 +3296,6 @@ void ui_block_cm_to_scene_linear_v3(uiBlock *block, float pixel[3])
IMB_colormanagement_display_to_scene_linear_v3(pixel, display);
}
-void ui_block_cm_to_display_space_range(uiBlock *block, float *min, float *max)
-{
- struct ColorManagedDisplay *display = ui_block_cm_display_get(block);
- float pixel[3];
-
- copy_v3_fl(pixel, *min);
- IMB_colormanagement_scene_linear_to_display_v3(pixel, display);
- *min = min_fff(UNPACK3(pixel));
-
- copy_v3_fl(pixel, *max);
- IMB_colormanagement_scene_linear_to_display_v3(pixel, display);
- *max = max_fff(UNPACK3(pixel));
-}
-
static uiBut *ui_but_alloc(const eButType type)
{
switch (type) {
diff --git a/source/blender/editors/interface/interface_draw.c b/source/blender/editors/interface/interface_draw.c
index ef9a69cd1dd..f1ada343faa 100644
--- a/source/blender/editors/interface/interface_draw.c
+++ b/source/blender/editors/interface/interface_draw.c
@@ -1404,15 +1404,12 @@ static void ui_draw_colorband_handle(
void ui_draw_but_COLORBAND(uiBut *but, uiWidgetColors *UNUSED(wcol), const rcti *rect)
{
- struct ColorManagedDisplay *display = NULL;
+ struct ColorManagedDisplay *display = ui_block_cm_display_get(but->block);
uint pos_id, col_id;
ColorBand *coba = (ColorBand *)(but->editcoba ? but->editcoba : but->poin);
if (coba == NULL) return;
- if (but->block->color_profile)
- display = ui_block_cm_display_get(but->block);
-
float x1 = rect->xmin;
float sizex = rect->xmax - x1;
float sizey = BLI_rcti_size_y(rect);
diff --git a/source/blender/editors/interface/interface_handlers.c b/source/blender/editors/interface/interface_handlers.c
index 3a3259e8d1f..3949c1e2d50 100644
--- a/source/blender/editors/interface/interface_handlers.c
+++ b/source/blender/editors/interface/interface_handlers.c
@@ -5440,7 +5440,6 @@ static bool ui_numedit_but_HSVCUBE(
float x, y;
float mx_fl, my_fl;
bool changed = true;
- bool use_display_colorspace = ui_but_is_colorpicker_display_space(but);
ui_mouse_scale_warp(data, mx, my, &mx_fl, &my_fl, shift);
@@ -5454,9 +5453,7 @@ static bool ui_numedit_but_HSVCUBE(
#endif
ui_but_v3_get(but, rgb);
-
- if (use_display_colorspace)
- ui_block_cm_to_display_space_v3(but->block, rgb);
+ ui_scene_linear_to_color_picker_space(but, rgb);
ui_rgb_to_color_picker_HSVCUBE_compat_v(but, rgb, hsv);
@@ -5469,8 +5466,7 @@ static bool ui_numedit_but_HSVCUBE(
/* calculate original hsv again */
copy_v3_v3(rgb, data->origvec);
- if (use_display_colorspace)
- ui_block_cm_to_display_space_v3(but->block, rgb);
+ ui_scene_linear_to_color_picker_space(but, rgb);
copy_v3_v3(hsvo, hsv);
@@ -5518,9 +5514,6 @@ static bool ui_numedit_but_HSVCUBE(
{
/* vertical 'value' strip */
float min = but->softmin, max = but->softmax;
- if (use_display_colorspace) {
- ui_block_cm_to_display_space_range(but->block, &min, &max);
- }
/* exception only for value strip - use the range set in but->min/max */
hsv[2] = y * (max - min) + min;
break;
@@ -5537,9 +5530,7 @@ static bool ui_numedit_but_HSVCUBE(
}
ui_color_picker_to_rgb_HSVCUBE_v(but, hsv, rgb);
-
- if (use_display_colorspace)
- ui_block_cm_to_scene_linear_v3(but->block, rgb);
+ ui_color_picker_to_scene_linear_space(but, rgb);
/* clamp because with color conversion we can exceed range [#34295] */
if (but->a1 == UI_GRAD_V_ALT) {
@@ -5565,13 +5556,9 @@ static void ui_ndofedit_but_HSVCUBE(
const float hsv_v_max = max_ff(hsv[2], but->softmax);
float rgb[3];
float sensitivity = (shift ? 0.15f : 0.3f) * ndof->dt;
- bool use_display_colorspace = ui_but_is_colorpicker_display_space(but);
ui_but_v3_get(but, rgb);
-
- if (use_display_colorspace)
- ui_block_cm_to_display_space_v3(but->block, rgb);
-
+ ui_scene_linear_to_color_picker_space(but, rgb);
ui_rgb_to_color_picker_HSVCUBE_compat_v(but, rgb, hsv);
switch ((int)but->a1) {
@@ -5620,9 +5607,7 @@ static void ui_ndofedit_but_HSVCUBE(
hsv_clamp_v(hsv, hsv_v_max);
ui_color_picker_to_rgb_HSVCUBE_v(but, hsv, rgb);
-
- if (use_display_colorspace)
- ui_block_cm_to_scene_linear_v3(but->block, rgb);
+ ui_color_picker_to_scene_linear_space(but, rgb);
copy_v3_v3(data->vec, rgb);
ui_but_v3_set(but, data->vec);
@@ -5737,7 +5722,6 @@ static bool ui_numedit_but_HSVCIRCLE(
float rgb[3];
ColorPicker *cpicker = but->custom_data;
float *hsv = cpicker->color_data;
- bool use_display_colorspace = ui_but_is_colorpicker_display_space(but);
ui_mouse_scale_warp(data, mx, my, &mx_fl, &my_fl, shift);
@@ -5760,9 +5744,7 @@ static bool ui_numedit_but_HSVCIRCLE(
BLI_rcti_rctf_copy(&rect, &but->rect);
ui_but_v3_get(but, rgb);
- if (use_display_colorspace)
- ui_block_cm_to_display_space_v3(but->block, rgb);
-
+ ui_scene_linear_to_color_picker_space(but, rgb);
ui_rgb_to_color_picker_compat_v(rgb, hsv);
/* exception, when using color wheel in 'locked' value state:
@@ -5784,9 +5766,7 @@ static bool ui_numedit_but_HSVCIRCLE(
/* calculate original hsv again */
copy_v3_v3(hsvo, hsv);
copy_v3_v3(rgbo, data->origvec);
- if (use_display_colorspace)
- ui_block_cm_to_display_space_v3(but->block, rgbo);
-
+ ui_scene_linear_to_color_picker_space(but, rgbo);
ui_rgb_to_color_picker_compat_v(rgbo, hsvo);
/* and original position */
@@ -5812,9 +5792,7 @@ static bool ui_numedit_but_HSVCIRCLE(
normalize_v3_length(rgb, but->a2);
}
- if (use_display_colorspace)
- ui_block_cm_to_scene_linear_v3(but->block, rgb);
-
+ ui_color_picker_to_scene_linear_space(but, rgb);
ui_but_v3_set(but, rgb);
data->draglastx = mx;
@@ -5831,14 +5809,12 @@ static void ui_ndofedit_but_HSVCIRCLE(
{
ColorPicker *cpicker = but->custom_data;
float *hsv = cpicker->color_data;
- bool use_display_colorspace = ui_but_is_colorpicker_display_space(but);
float rgb[3];
float phi, r /*, sqr */ /* UNUSED */, v[2];
float sensitivity = (shift ? 0.06f : 0.3f) * ndof->dt;
ui_but_v3_get(but, rgb);
- if (use_display_colorspace)
- ui_block_cm_to_display_space_v3(but->block, rgb);
+ ui_scene_linear_to_color_picker_space(but, rgb);
ui_rgb_to_color_picker_compat_v(rgb, hsv);
/* Convert current color on hue/sat disc to circular coordinates phi, r */
@@ -5889,9 +5865,7 @@ static void ui_ndofedit_but_HSVCIRCLE(
normalize_v3_length(data->vec, but->a2);
}
- if (use_display_colorspace)
- ui_block_cm_to_scene_linear_v3(but->block, data->vec);
-
+ ui_color_picker_to_scene_linear_space(but, data->vec);
ui_but_v3_set(but, data->vec);
}
#endif /* WITH_INPUT_NDOF */
diff --git a/source/blender/editors/interface/interface_intern.h b/source/blender/editors/interface/interface_intern.h
index 7e8653bfc56..0ab92a633ad 100644
--- a/source/blender/editors/interface/interface_intern.h
+++ b/source/blender/editors/interface/interface_intern.h
@@ -439,7 +439,7 @@ struct uiBlock {
struct UnitSettings *unit; /* unit system, used a lot for numeric buttons so include here rather then fetching through the scene every time. */
ColorPickerData color_pickers; /* XXX, only accessed by color picker templates */
- bool color_profile; /* color profile for correcting linear colors for display */
+ bool is_color_gamma_picker; /* Block for color picker with gamma baked in. */
char display_device[64]; /* display device name used to display this block,
* used by color widgets to transform colors from/to scene linear
@@ -477,7 +477,6 @@ extern void ui_hsvcircle_vals_from_pos(
const float mx, const float my);
extern void ui_hsvcircle_pos_from_vals(struct uiBut *but, const rcti *rect, float *hsv, float *xpos, float *ypos);
extern void ui_hsvcube_pos_from_vals(struct uiBut *but, const rcti *rect, float *hsv, float *xp, float *yp);
-bool ui_but_is_colorpicker_display_space(struct uiBut *but);
extern void ui_but_string_get_ex(
uiBut *but, char *str, const size_t maxlen,
@@ -516,7 +515,6 @@ extern void ui_block_bounds_calc(uiBlock *block);
extern struct ColorManagedDisplay *ui_block_cm_display_get(uiBlock *block);
void ui_block_cm_to_display_space_v3(uiBlock *block, float pixel[3]);
void ui_block_cm_to_scene_linear_v3(uiBlock *block, float pixel[3]);
-void ui_block_cm_to_display_space_range(uiBlock *block, float *min, float *max);
/* interface_regions.c */
@@ -611,6 +609,11 @@ void ui_rgb_to_color_picker_v(const float rgb[3], float r_cp[3]);
void ui_color_picker_to_rgb_v(const float r_cp[3], float rgb[3]);
void ui_color_picker_to_rgb(float r_cp0, float r_cp1, float r_cp2, float *r, float *g, float *b);
+bool ui_but_is_color_gamma(uiBut *but);
+
+void ui_scene_linear_to_color_picker_space(uiBut *but, float rgb[3]);
+void ui_color_picker_to_scene_linear_space(uiBut *but, float rgb[3]);
+
uiBlock *ui_block_func_COLOR(struct bContext *C, uiPopupBlockHandle *handle, void *arg_but);
ColorPicker *ui_block_colorpicker_create(struct uiBlock *block);
diff --git a/source/blender/editors/interface/interface_region_color_picker.c b/source/blender/editors/interface/interface_region_color_picker.c
index a99bcb2b73c..7c2afaf1a92 100644
--- a/source/blender/editors/interface/interface_region_color_picker.c
+++ b/source/blender/editors/interface/interface_region_color_picker.c
@@ -111,6 +111,36 @@ void ui_color_picker_to_rgb(float r_cp0, float r_cp1, float r_cp2, float *r, flo
}
}
+/* Returns true if the button is for a color with gamma baked in,
+ * or if it's a color picker for such a button. */
+bool ui_but_is_color_gamma(uiBut *but)
+{
+ if (but->rnaprop) {
+ if (RNA_property_subtype(but->rnaprop) == PROP_COLOR_GAMMA) {
+ return true;
+ }
+ }
+
+ return but->block->is_color_gamma_picker;
+}
+
+void ui_scene_linear_to_color_picker_space(uiBut *but, float rgb[3])
+{
+ /* Map to color picking space for HSV values and HSV cube/circle,
+ * assuming it is more perceptually linear then the scene linear
+ * space for intuitive color picking. */
+ if (!ui_but_is_color_gamma(but)) {
+ IMB_colormanagement_scene_linear_to_color_picking_v3(rgb);
+ }
+}
+
+void ui_color_picker_to_scene_linear_space(uiBut *but, float rgb[3])
+{
+ if (!ui_but_is_color_gamma(but)) {
+ IMB_colormanagement_color_picking_to_scene_linear_v3(rgb);
+ }
+}
+
/** \} */
/* -------------------------------------------------------------------- */
@@ -132,28 +162,18 @@ void ui_but_hsv_set(uiBut *but)
/* Updates all buttons who share the same color picker as the one passed
* also used by small picker, be careful with name checks below... */
static void ui_update_color_picker_buts_rgb(
- uiBlock *block, ColorPicker *cpicker, const float rgb[3], bool is_display_space)
+ uiBut *from_but, uiBlock *block, ColorPicker *cpicker, const float rgb[3])
{
uiBut *bt;
float *hsv = cpicker->color_data;
- struct ColorManagedDisplay *display = NULL;
- /* this is to keep the H and S value when V is equal to zero
- * and we are working in HSV mode, of course!
- */
- if (is_display_space) {
- ui_rgb_to_color_picker_compat_v(rgb, hsv);
- }
- else {
- /* we need to convert to display space to use hsv, because hsv is stored in display space */
- float rgb_display[3];
- copy_v3_v3(rgb_display, rgb);
- ui_block_cm_to_display_space_v3(block, rgb_display);
- ui_rgb_to_color_picker_compat_v(rgb_display, hsv);
+ /* Convert from RGB to HSV in perceptually linear space. */
+ float tmp[3];
+ copy_v3_v3(tmp, rgb);
+ if (from_but) {
+ ui_scene_linear_to_color_picker_space(from_but, tmp);
}
-
- if (block->color_profile)
- display = ui_block_cm_display_get(block);
+ ui_rgb_to_color_picker_compat_v(tmp, hsv);
/* this updates button strings, is hackish... but button pointers are on stack of caller function */
for (bt = block->buttons.first; bt; bt = bt->next) {
@@ -177,9 +197,9 @@ static void ui_update_color_picker_buts_rgb(
copy_v3_v3(rgb_gamma, rgb);
- if (display) {
+ if (!block->is_color_gamma_picker) {
/* make a display version, for Hex code */
- IMB_colormanagement_scene_linear_to_display_v3(rgb_gamma, display);
+ ui_block_cm_to_display_space_v3(block, rgb_gamma);
}
if (rgb_gamma[0] > 1.0f) rgb_gamma[0] = modf(rgb_gamma[0], &intpart);
@@ -230,7 +250,7 @@ static void ui_colorpicker_rna_cb(bContext *UNUSED(C), void *bt1, void *UNUSED(a
if (prop) {
RNA_property_float_get_array(&ptr, prop, rgb);
ui_update_color_picker_buts_rgb(
- but->block, but->custom_data, rgb, (RNA_property_subtype(prop) == PROP_COLOR_GAMMA));
+ but, but->block, but->custom_data, rgb);
}
if (popup)
@@ -244,16 +264,13 @@ static void ui_color_wheel_rna_cb(bContext *UNUSED(C), void *bt1, void *UNUSED(a
float rgb[3];
ColorPicker *cpicker = but->custom_data;
float *hsv = cpicker->color_data;
- bool use_display_colorspace = ui_but_is_colorpicker_display_space(but);
ui_color_picker_to_rgb_v(hsv, rgb);
- /* hsv is saved in display space so convert back */
- if (use_display_colorspace) {
- ui_block_cm_to_scene_linear_v3(but->block, rgb);
- }
+ /* hsv is saved in perceptually linear space so convert back */
+ ui_color_picker_to_scene_linear_space(but, rgb);
- ui_update_color_picker_buts_rgb(but->block, cpicker, rgb, !use_display_colorspace);
+ ui_update_color_picker_buts_rgb(but, but->block, cpicker, rgb);
if (popup)
popup->menuretval = UI_RETURN_UPDATE;
@@ -270,12 +287,12 @@ static void ui_colorpicker_hex_rna_cb(bContext *UNUSED(C), void *bt1, void *hexc
hex_to_rgb(hexcol, rgb, rgb + 1, rgb + 2);
/* Hex code is assumed to be in sRGB space (coming from other applications, web, etc) */
- if (but->block->color_profile) {
+ if (!but->block->is_color_gamma_picker) {
/* so we need to linearise it for Blender */
ui_block_cm_to_scene_linear_v3(but->block, rgb);
}
- ui_update_color_picker_buts_rgb(but->block, cpicker, rgb, false);
+ ui_update_color_picker_buts_rgb(NULL, but->block, cpicker, rgb);
if (popup)
popup->menuretval = UI_RETURN_UPDATE;
@@ -378,37 +395,22 @@ static void ui_colorpicker_square(uiBlock *block, PointerRNA *ptr, PropertyRNA *
/* a HS circle, V slider, rgb/hsv/hex sliders */
static void ui_block_colorpicker(
- uiBlock *block, float rgba[4], PointerRNA *ptr, PropertyRNA *prop, bool show_picker)
+ uiBlock *block, uiBut *from_but, float rgba[4], bool show_picker)
{
static short colormode = 0; /* temp? 0=rgb, 1=hsv, 2=hex */
uiBut *bt;
int width, butwidth;
- static char tip[50];
static char hexcol[128];
- float rgb_gamma[3];
- unsigned char rgb_gamma_uchar[3];
float softmin, softmax, hardmin, hardmax, step, precision;
int yco;
ColorPicker *cpicker = ui_block_colorpicker_create(block);
float *hsv = cpicker->color_data;
+ PointerRNA *ptr = &from_but->rnapoin;
+ PropertyRNA *prop = from_but->rnaprop;
width = PICKER_TOTAL_W;
butwidth = width - 1.5f * UI_UNIT_X;
- /* existence of profile means storage is in linear color space, with display correction */
- /* XXX That tip message is not use anywhere! */
- if (!block->color_profile) {
- BLI_strncpy(tip, N_("Value in Display Color Space"), sizeof(tip));
- copy_v3_v3(rgb_gamma, rgba);
- }
- else {
- BLI_strncpy(tip, N_("Value in Linear RGB Color Space"), sizeof(tip));
-
- /* make a display version, for Hex code */
- copy_v3_v3(rgb_gamma, rgba);
- ui_block_cm_to_display_space_v3(block, rgb_gamma);
- }
-
/* sneaky way to check for alpha */
rgba[3] = FLT_MAX;
@@ -416,6 +418,11 @@ static void ui_block_colorpicker(
RNA_property_float_range(ptr, prop, &hardmin, &hardmax);
RNA_property_float_get_array(ptr, prop, rgba);
+ float rgb_perceptual[3];
+ copy_v3_v3(rgb_perceptual, rgba);
+ ui_scene_linear_to_color_picker_space(from_but, rgb_perceptual);
+ ui_rgb_to_color_picker_v(rgb_perceptual, hsv);
+
/* when the softmax isn't defined in the RNA,
* using very large numbers causes sRGB/linear round trip to fail. */
if (softmax == FLT_MAX) {
@@ -539,6 +546,19 @@ static void ui_block_colorpicker(
rgba[3] = 1.0f;
}
+ /* Hex color is in display space. This should actually be sRGB without any view
+ * transform, as most other applications would expect this. */
+ float rgb_gamma[3];
+ unsigned char rgb_gamma_uchar[3];
+
+ if (block->is_color_gamma_picker) {
+ copy_v3_v3(rgb_gamma, rgba);
+ }
+ else {
+ copy_v3_v3(rgb_gamma, rgba);
+ ui_block_cm_to_display_space_v3(block, rgb_gamma);
+ }
+
rgb_float_to_uchar(rgb_gamma_uchar, rgb_gamma);
BLI_snprintf(hexcol, sizeof(hexcol), "%02X%02X%02X", UNPACK3_EX((uint), rgb_gamma_uchar, ));
@@ -552,8 +572,6 @@ static void ui_block_colorpicker(
block, UI_BTYPE_LABEL, 0, IFACE_("(Gamma Corrected)"), 0, yco - UI_UNIT_Y,
butwidth, UI_UNIT_Y, NULL, 0.0, 0.0, 0, 0, "");
- ui_rgb_to_color_picker_v(rgb_gamma, hsv);
-
ui_colorpicker_hide_reveal(block, colormode);
}
@@ -576,24 +594,18 @@ static int ui_colorpicker_small_wheel_cb(const bContext *UNUSED(C), uiBlock *blo
float rgb[3];
ColorPicker *cpicker = but->custom_data;
float *hsv = cpicker->color_data;
- bool use_display_colorspace = ui_but_is_colorpicker_display_space(but);
ui_but_v3_get(but, rgb);
-
- if (use_display_colorspace)
- ui_block_cm_to_display_space_v3(block, rgb);
-
+ ui_scene_linear_to_color_picker_space(but, rgb);
ui_rgb_to_color_picker_compat_v(rgb, hsv);
hsv[2] = clamp_f(hsv[2] + add, 0.0f, 1.0f);
- ui_color_picker_to_rgb_v(hsv, rgb);
-
- if (use_display_colorspace)
- ui_block_cm_to_scene_linear_v3(block, rgb);
+ ui_color_picker_to_rgb_v(hsv, rgb);
+ ui_color_picker_to_scene_linear_space(but, rgb);
ui_but_v3_set(but, rgb);
- ui_update_color_picker_buts_rgb(block, cpicker, rgb, !use_display_colorspace);
+ ui_update_color_picker_buts_rgb(but, block, cpicker, rgb);
if (popup)
popup->menuretval = UI_RETURN_UPDATE;
@@ -612,8 +624,8 @@ uiBlock *ui_block_func_COLOR(bContext *C, uiPopupBlockHandle *handle, void *arg_
block = UI_block_begin(C, handle->region, __func__, UI_EMBOSS);
- if (RNA_property_subtype(but->rnaprop) == PROP_COLOR_GAMMA) {
- block->color_profile = false;
+ if (ui_but_is_color_gamma(but)) {
+ block->is_color_gamma_picker = true;
}
if (but->block) {
@@ -626,7 +638,7 @@ uiBlock *ui_block_func_COLOR(bContext *C, uiPopupBlockHandle *handle, void *arg_
copy_v3_v3(handle->retvec, but->editvec);
- ui_block_colorpicker(block, handle->retvec, &but->rnapoin, but->rnaprop, show_picker);
+ ui_block_colorpicker(block, but, handle->retvec, show_picker);
block->flag = UI_BLOCK_LOOP | UI_BLOCK_KEEP_OPEN | UI_BLOCK_OUT_1 | UI_BLOCK_MOVEMOUSE_QUIT;
UI_block_theme_style_set(block, UI_BLOCK_THEME_STYLE_POPUP);
diff --git a/source/blender/editors/interface/interface_widgets.c b/source/blender/editors/interface/interface_widgets.c
index f9a96803661..fd34ac8f140 100644
--- a/source/blender/editors/interface/interface_widgets.c
+++ b/source/blender/editors/interface/interface_widgets.c
@@ -2581,23 +2581,16 @@ static void ui_draw_but_HSVCIRCLE(uiBut *but, uiWidgetColors *wcol, const rcti *
float radius = (float)min_ii(BLI_rcti_size_x(rect), BLI_rcti_size_y(rect)) / 2.0f;
ColorPicker *cpicker = but->custom_data;
- const float *hsv_ptr = cpicker->color_data;
- float rgb[3], hsvo[3], hsv[3], col[3], colcent[3];
- bool color_profile = ui_but_is_colorpicker_display_space(but);
+ float rgb[3], hsv[3], rgb_center[3];
+ bool is_color_gamma = ui_but_is_color_gamma(but);
- /* color */
- ui_but_v3_get(but, rgb);
-
- /* since we use compat functions on both 'hsv' and 'hsvo', they need to be initialized */
- hsvo[0] = hsv[0] = hsv_ptr[0];
- hsvo[1] = hsv[1] = hsv_ptr[1];
- hsvo[2] = hsv[2] = hsv_ptr[2];
-
- if (color_profile)
- ui_block_cm_to_display_space_v3(but->block, rgb);
+ /* Initialize for compatibility. */
+ copy_v3_v3(hsv, cpicker->color_data);
+ /* Compute current hue. */
+ ui_but_v3_get(but, rgb);
+ ui_scene_linear_to_color_picker_space(but, rgb);
ui_rgb_to_color_picker_compat_v(rgb, hsv);
- copy_v3_v3(hsvo, hsv);
CLAMP(hsv[2], 0.0f, 1.0f); /* for display only */
@@ -2611,7 +2604,13 @@ static void ui_draw_but_HSVCIRCLE(uiBut *but, uiWidgetColors *wcol, const rcti *
hsv[2] = 0.5f;
}
- ui_color_picker_to_rgb(0.0f, 0.0f, hsv[2], colcent, colcent + 1, colcent + 2);
+ const float hsv_center[3] = {0.0f, 0.0f, hsv[2]};
+ ui_color_picker_to_rgb_v(hsv_center, rgb_center);
+ ui_scene_linear_to_color_picker_space(but, rgb_center);
+
+ if (!is_color_gamma) {
+ ui_block_cm_to_display_space_v3(but->block, rgb_center);
+ }
GPUVertFormat *format = immVertexFormat();
uint pos = GPU_vertformat_attr_add(format, "pos", GPU_COMP_F32, 2, GPU_FETCH_FLOAT);
@@ -2620,19 +2619,27 @@ static void ui_draw_but_HSVCIRCLE(uiBut *but, uiWidgetColors *wcol, const rcti *
immBindBuiltinProgram(GPU_SHADER_2D_SMOOTH_COLOR);
immBegin(GPU_PRIM_TRI_FAN, tot + 2);
- immAttr3fv(color, colcent);
+ immAttr3fv(color, rgb_center);
immVertex2f(pos, centx, centy);
float ang = 0.0f;
for (int a = 0; a <= tot; a++, ang += radstep) {
float si = sinf(ang);
float co = cosf(ang);
+ float hsv_ang[3];
+ float rgb_ang[3];
- ui_hsvcircle_vals_from_pos(hsv, hsv + 1, rect, centx + co * radius, centy + si * radius);
+ ui_hsvcircle_vals_from_pos(hsv_ang, hsv_ang + 1, rect, centx + co * radius, centy + si * radius);
+ hsv_ang[2] = hsv[2];
- ui_color_picker_to_rgb_v(hsv, col);
+ ui_color_picker_to_rgb_v(hsv_ang, rgb_ang);
+ ui_color_picker_to_scene_linear_space(but, rgb_ang);
- immAttr3fv(color, col);
+ if (!is_color_gamma) {
+ ui_block_cm_to_display_space_v3(but->block, rgb_ang);
+ }
+
+ immAttr3fv(color, rgb_ang);
immVertex2f(pos, centx + co * radius, centy + si * radius);
}
immEnd();
@@ -2656,8 +2663,13 @@ static void ui_draw_but_HSVCIRCLE(uiBut *but, uiWidgetColors *wcol, const rcti *
GPU_line_smooth(false);
/* cursor */
+ copy_v3_v3(hsv, cpicker->color_data);
+ ui_but_v3_get(but, rgb);
+ ui_scene_linear_to_color_picker_space(but, rgb);
+ ui_rgb_to_color_picker_compat_v(rgb, hsv);
+
float xpos, ypos;
- ui_hsvcircle_pos_from_vals(but, rect, hsvo, &xpos, &ypos);
+ ui_hsvcircle_pos_from_vals(but, rect, hsv, &xpos, &ypos);
ui_hsv_cursor(xpos, ypos);
}
@@ -2812,18 +2824,6 @@ void ui_draw_gradient(const rcti *rect, const float hsv[3], const int type, cons
immUnbindProgram();
}
-bool ui_but_is_colorpicker_display_space(uiBut *but)
-{
- bool color_profile = but->block->color_profile;
-
- if (but->rnaprop) {
- if (RNA_property_subtype(but->rnaprop) == PROP_COLOR_GAMMA)
- color_profile = false;
- }
-
- return color_profile;
-}
-
void ui_hsvcube_pos_from_vals(uiBut *but, const rcti *rect, float *hsv, float *xp, float *yp)
{
float x = 0.0f, y = 0.0f;
@@ -2865,15 +2865,12 @@ static void ui_draw_but_HSVCUBE(uiBut *but, const rcti *rect)
ColorPicker *cpicker = but->custom_data;
float *hsv = cpicker->color_data;
float hsv_n[3];
- bool use_display_colorspace = ui_but_is_colorpicker_display_space(but);
+ /* Initialize for compatibility. */
copy_v3_v3(hsv_n, hsv);
ui_but_v3_get(but, rgb);
-
- if (use_display_colorspace)
- ui_block_cm_to_display_space_v3(but->block, rgb);
-
+ ui_scene_linear_to_color_picker_space(but, rgb);
rgb_to_hsv_compat_v(rgb, hsv_n);
ui_draw_gradient(rect, hsv_n, but->a1, 1.0f);
@@ -2901,15 +2898,9 @@ static void ui_draw_but_HSV_v(uiBut *but, const rcti *rect)
const float rad = wcol->roundness * BLI_rcti_size_x(rect);
float x, y;
float rgb[3], hsv[3], v;
- bool color_profile = but->block->color_profile;
-
- if (but->rnaprop && RNA_property_subtype(but->rnaprop) == PROP_COLOR_GAMMA)
- color_profile = false;
ui_but_v3_get(but, rgb);
-
- if (color_profile)
- ui_block_cm_to_display_space_v3(but->block, rgb);
+ ui_scene_linear_to_color_picker_space(but, rgb);
if (but->a1 == UI_GRAD_L_ALT)
rgb_to_hsl_v(rgb, hsv);
@@ -2920,9 +2911,6 @@ static void ui_draw_but_HSV_v(uiBut *but, const rcti *rect)
/* map v from property range to [0,1] */
if (but->a1 == UI_GRAD_V_ALT) {
float min = but->softmin, max = but->softmax;
- if (color_profile) {
- ui_block_cm_to_display_space_range(but->block, &min, &max);
- }
v = (v - min) / (max - min);
}
@@ -3378,16 +3366,12 @@ static void widget_swatch(uiBut *but, uiWidgetColors *wcol, rcti *rect, int stat
{
uiWidgetBase wtb;
float rad, col[4];
- bool color_profile = but->block->color_profile;
col[3] = 1.0f;
if (but->rnaprop) {
BLI_assert(but->rnaindex == -1);
- if (RNA_property_subtype(but->rnaprop) == PROP_COLOR_GAMMA)
- color_profile = false;
-
if (RNA_property_array_length(&but->rnapoin, but->rnaprop) == 4) {
col[3] = RNA_property_float_get_index(&but->rnapoin, but->rnaprop, 3);
}
@@ -3415,7 +3399,7 @@ static void widget_swatch(uiBut *but, uiWidgetColors *wcol, rcti *rect, int stat
round_box_edges(&wtb, roundboxalign, rect, rad);
}
- if (color_profile)
+ if (!ui_but_is_color_gamma(but))
ui_block_cm_to_display_space_v3(but->block, col);
rgba_float_to_uchar((unsigned char *)wcol->inner, col);
diff --git a/source/blender/imbuf/IMB_colormanagement.h b/source/blender/imbuf/IMB_colormanagement.h
index 8c903af2420..29e54158f4b 100644
--- a/source/blender/imbuf/IMB_colormanagement.h
+++ b/source/blender/imbuf/IMB_colormanagement.h
@@ -96,6 +96,9 @@ void IMB_colormanagement_scene_linear_to_colorspace_v3(float pixel[3], struct Co
void IMB_colormanagement_colorspace_to_scene_linear(float *buffer, int width, int height, int channels, struct ColorSpace *colorspace, bool predivide);
+void IMB_colormanagement_scene_linear_to_color_picking_v3(float pixel[3]);
+void IMB_colormanagement_color_picking_to_scene_linear_v3(float pixel[3]);
+
void IMB_colormanagement_scene_linear_to_display_v3(float pixel[3], struct ColorManagedDisplay *display);
void IMB_colormanagement_display_to_scene_linear_v3(float pixel[3], struct ColorManagedDisplay *display);
diff --git a/source/blender/imbuf/intern/colormanagement.c b/source/blender/imbuf/intern/colormanagement.c
index 5d0e59e1788..f2244b6ab5c 100644
--- a/source/blender/imbuf/intern/colormanagement.c
+++ b/source/blender/imbuf/intern/colormanagement.c
@@ -130,7 +130,14 @@ static struct global_glsl_state {
/* Container for GLSL state needed for OCIO module. */
struct OCIO_GLSLDrawState *ocio_glsl_state;
struct OCIO_GLSLDrawState *transform_ocio_glsl_state;
-} global_glsl_state;
+} global_glsl_state = {NULL};
+
+static struct global_color_picking_state {
+ /* Cached processor for color picking conversion. */
+ OCIO_ConstProcessorRcPtr *processor_to;
+ OCIO_ConstProcessorRcPtr *processor_from;
+ bool failed;
+} global_color_picking_state = {NULL};
/*********************** Color managed cache *************************/
@@ -699,6 +706,15 @@ void colormanagement_exit(void)
if (global_glsl_state.transform_ocio_glsl_state)
OCIO_freeOGLState(global_glsl_state.transform_ocio_glsl_state);
+ if (global_color_picking_state.processor_to)
+ OCIO_processorRelease(global_color_picking_state.processor_to);
+
+ if (global_color_picking_state.processor_from)
+ OCIO_processorRelease(global_color_picking_state.processor_from);
+
+ memset(&global_glsl_state, 0, sizeof(global_glsl_state));
+ memset(&global_color_picking_state, 0, sizeof(global_color_picking_state));
+
colormanage_free_config();
}
@@ -1911,6 +1927,54 @@ void IMB_colormanagement_colorspace_to_scene_linear(float *buffer, int width, in
}
}
+void IMB_colormanagement_scene_linear_to_color_picking_v3(float pixel[3])
+{
+ if (!global_color_picking_state.processor_to && !global_color_picking_state.failed) {
+ /* Create processor if none exists. */
+ BLI_mutex_lock(&processor_lock);
+
+ if (!global_color_picking_state.processor_to && !global_color_picking_state.failed) {
+ global_color_picking_state.processor_to =
+ create_colorspace_transform_processor(global_role_scene_linear,
+ global_role_color_picking);
+
+ if (!global_color_picking_state.processor_to) {
+ global_color_picking_state.failed = true;
+ }
+ }
+
+ BLI_mutex_unlock(&processor_lock);
+ }
+
+ if (global_color_picking_state.processor_to) {
+ OCIO_processorApplyRGB(global_color_picking_state.processor_to, pixel);
+ }
+}
+
+void IMB_colormanagement_color_picking_to_scene_linear_v3(float pixel[3])
+{
+ if (!global_color_picking_state.processor_from && !global_color_picking_state.failed) {
+ /* Create processor if none exists. */
+ BLI_mutex_lock(&processor_lock);
+
+ if (!global_color_picking_state.processor_from && !global_color_picking_state.failed) {
+ global_color_picking_state.processor_from =
+ create_colorspace_transform_processor(global_role_color_picking,
+ global_role_scene_linear);
+
+ if (!global_color_picking_state.processor_from) {
+ global_color_picking_state.failed = true;
+ }
+ }
+
+ BLI_mutex_unlock(&processor_lock);
+ }
+
+ if (global_color_picking_state.processor_from) {
+ OCIO_processorApplyRGB(global_color_picking_state.processor_from, pixel);
+ }
+}
+
/* convert pixel from scene linear to display space using default view
* used by performance-critical areas such as color-related widgets where we want to reduce
* amount of per-widget allocations