Compositor: Full frame Color Correction node

Adds full frame implementation to this node operation.
No functional changes.
1.4x faster than tiled fallback.

Reviewed By: jbakker

Differential Revision: https://developer.blender.org/D11765
This commit is contained in:
Manuel Castilla 2021-07-05 21:02:22 +02:00
parent bf75106ae9
commit 0c90aa097d
2 changed files with 84 additions and 2 deletions

View File

@ -157,6 +157,86 @@ void ColorCorrectionOperation::executePixelSampled(float output[4],
output[3] = inputImageColor[3];
}
void ColorCorrectionOperation::update_memory_buffer_row(PixelCursor &p)
{
for (; p.out < p.row_end; p.next()) {
const float *in_color = p.ins[0];
const float *in_mask = p.ins[1];
const float level = (in_color[0] + in_color[1] + in_color[2]) / 3.0f;
float level_shadows = 0.0f;
float level_midtones = 0.0f;
float level_highlights = 0.0f;
constexpr float MARGIN = 0.10f;
constexpr float MARGIN_DIV = 0.5f / MARGIN;
if (level < this->m_data->startmidtones - MARGIN) {
level_shadows = 1.0f;
}
else if (level < this->m_data->startmidtones + MARGIN) {
level_midtones = ((level - this->m_data->startmidtones) * MARGIN_DIV) + 0.5f;
level_shadows = 1.0f - level_midtones;
}
else if (level < this->m_data->endmidtones - MARGIN) {
level_midtones = 1.0f;
}
else if (level < this->m_data->endmidtones + MARGIN) {
level_highlights = ((level - this->m_data->endmidtones) * MARGIN_DIV) + 0.5f;
level_midtones = 1.0f - level_highlights;
}
else {
level_highlights = 1.0f;
}
float contrast = this->m_data->master.contrast;
float saturation = this->m_data->master.saturation;
float gamma = this->m_data->master.gamma;
float gain = this->m_data->master.gain;
float lift = this->m_data->master.lift;
contrast *= level_shadows * this->m_data->shadows.contrast +
level_midtones * this->m_data->midtones.contrast +
level_highlights * this->m_data->highlights.contrast;
saturation *= level_shadows * this->m_data->shadows.saturation +
level_midtones * this->m_data->midtones.saturation +
level_highlights * this->m_data->highlights.saturation;
gamma *= level_shadows * this->m_data->shadows.gamma +
level_midtones * this->m_data->midtones.gamma +
level_highlights * this->m_data->highlights.gamma;
gain *= level_shadows * this->m_data->shadows.gain +
level_midtones * this->m_data->midtones.gain +
level_highlights * this->m_data->highlights.gain;
lift += level_shadows * this->m_data->shadows.lift +
level_midtones * this->m_data->midtones.lift +
level_highlights * this->m_data->highlights.lift;
const float inv_gamma = 1.0f / gamma;
const float luma = IMB_colormanagement_get_luminance(in_color);
float r = luma + saturation * (in_color[0] - luma);
float g = luma + saturation * (in_color[1] - luma);
float b = luma + saturation * (in_color[2] - luma);
r = 0.5f + (r - 0.5f) * contrast;
g = 0.5f + (g - 0.5f) * contrast;
b = 0.5f + (b - 0.5f) * contrast;
/* Check for negative values to avoid nan. */
r = color_correct_powf_safe(r * gain + lift, inv_gamma, r);
g = color_correct_powf_safe(g * gain + lift, inv_gamma, g);
b = color_correct_powf_safe(b * gain + lift, inv_gamma, b);
/* Mix with mask. */
const float value = MIN2(1.0f, in_mask[0]);
const float m_value = 1.0f - value;
r = m_value * in_color[0] + value * r;
g = m_value * in_color[1] + value * g;
b = m_value * in_color[2] + value * b;
p.out[0] = m_redChannelEnabled ? r : in_color[0];
p.out[1] = m_greenChannelEnabled ? g : in_color[1];
p.out[2] = m_blueChannelEnabled ? b : in_color[2];
p.out[3] = in_color[3];
}
}
void ColorCorrectionOperation::deinitExecution()
{
this->m_inputImage = nullptr;

View File

@ -18,11 +18,11 @@
#pragma once
#include "COM_NodeOperation.h"
#include "COM_MultiThreadedRowOperation.h"
namespace blender::compositor {
class ColorCorrectionOperation : public NodeOperation {
class ColorCorrectionOperation : public MultiThreadedRowOperation {
private:
/**
* Cached reference to the inputProgram
@ -69,6 +69,8 @@ class ColorCorrectionOperation : public NodeOperation {
{
this->m_blueChannelEnabled = enabled;
}
void update_memory_buffer_row(PixelCursor &p) override;
};
} // namespace blender::compositor