compositor color curve was MEM_dupallocN'ing the curve for every pixel calculation (when there were black or white inputs on the curve node).
avoid allocation by using local vars for black/white storage & curve calculation.
This commit is contained in:
parent
49d3766ceb
commit
988df24551
|
@ -53,6 +53,7 @@ void curvemapping_free_data(struct CurveMapping *cumap);
|
|||
void curvemapping_free(struct CurveMapping *cumap);
|
||||
void curvemapping_copy_data(struct CurveMapping *target, struct CurveMapping *cumap);
|
||||
struct CurveMapping *curvemapping_copy(struct CurveMapping *cumap);
|
||||
void curvemapping_set_black_white_ex(const float black[3], const float white[3], float r_bwmul[3]);
|
||||
void curvemapping_set_black_white(struct CurveMapping *cumap, const float black[3], const float white[3]);
|
||||
|
||||
#define CURVEMAP_SLOPE_NEGATIVE 0
|
||||
|
@ -73,6 +74,8 @@ float curvemapping_evaluateF(struct CurveMapping *cumap, int cur,
|
|||
void curvemapping_evaluate3F(struct CurveMapping *cumap, float vecout[3], const float vecin[3]);
|
||||
void curvemapping_evaluateRGBF(struct CurveMapping *cumap, float vecout[3], const float vecin[3]);
|
||||
void curvemapping_evaluate_premulRGB(struct CurveMapping *cumap, unsigned char vecout_byte[3], const unsigned char vecin_byte[3]);
|
||||
void curvemapping_evaluate_premulRGBF_ex(struct CurveMapping *cumap, float vecout[3], const float vecin[3],
|
||||
const float black[3], const float bwmul[3]);
|
||||
void curvemapping_evaluate_premulRGBF(struct CurveMapping *cumap, float vecout[3], const float vecin[3]);
|
||||
void curvemapping_do_ibuf(struct CurveMapping *cumap, struct ImBuf *ibuf);
|
||||
void curvemapping_premultiply(struct CurveMapping *cumap, int restore);
|
||||
|
|
|
@ -145,21 +145,31 @@ CurveMapping *curvemapping_copy(CurveMapping *cumap)
|
|||
return NULL;
|
||||
}
|
||||
|
||||
void curvemapping_set_black_white(CurveMapping *cumap, const float black[3], const float white[3])
|
||||
void curvemapping_set_black_white_ex(const float black[3], const float white[3], float r_bwmul[3])
|
||||
{
|
||||
int a;
|
||||
|
||||
if (white)
|
||||
copy_v3_v3(cumap->white, white);
|
||||
if (black)
|
||||
copy_v3_v3(cumap->black, black);
|
||||
|
||||
|
||||
for (a = 0; a < 3; a++) {
|
||||
if (cumap->white[a] == cumap->black[a])
|
||||
cumap->bwmul[a] = 0.0f;
|
||||
else
|
||||
cumap->bwmul[a] = 1.0f / (cumap->white[a] - cumap->black[a]);
|
||||
}
|
||||
const float delta = white[a] - black[a];
|
||||
if (delta != 0.0f) {
|
||||
r_bwmul[a] = 1.0f / delta;
|
||||
}
|
||||
else {
|
||||
r_bwmul[a] = 0.0f;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
void curvemapping_set_black_white(CurveMapping *cumap, const float black[3], const float white[3])
|
||||
{
|
||||
if (white) {
|
||||
copy_v3_v3(cumap->white, white);
|
||||
}
|
||||
if (black) {
|
||||
copy_v3_v3(cumap->black, black);
|
||||
}
|
||||
|
||||
curvemapping_set_black_white_ex(cumap->black, cumap->white, cumap->bwmul);
|
||||
}
|
||||
|
||||
/* ***************** operations on single curve ************* */
|
||||
|
@ -785,6 +795,29 @@ void curvemapping_evaluateRGBF(CurveMapping *cumap, float vecout[3], const float
|
|||
vecout[2] = curvemapping_evaluateF(cumap, 2, curvemapping_evaluateF(cumap, 3, vecin[2]));
|
||||
}
|
||||
|
||||
/** same as #curvemapping_evaluate_premulRGBF
|
||||
* but black/bwmul are passed as args for the compositor
|
||||
* where they can change per pixel.
|
||||
*
|
||||
* Use in conjunction with #curvemapping_set_black_white_ex
|
||||
*
|
||||
* \param black Use instead of cumap->black
|
||||
* \param bwmul Use instead of cumap->bwmul
|
||||
*/
|
||||
void curvemapping_evaluate_premulRGBF_ex(CurveMapping *cumap, float vecout[3], const float vecin[3],
|
||||
const float black[3], const float bwmul[3])
|
||||
{
|
||||
float fac;
|
||||
|
||||
fac = (vecin[0] - black[0]) * bwmul[0];
|
||||
vecout[0] = curvemap_evaluateF(cumap->cm, fac);
|
||||
|
||||
fac = (vecin[1] - black[1]) * bwmul[1];
|
||||
vecout[1] = curvemap_evaluateF(cumap->cm + 1, fac);
|
||||
|
||||
fac = (vecin[2] - black[2]) * bwmul[2];
|
||||
vecout[2] = curvemap_evaluateF(cumap->cm + 2, fac);
|
||||
}
|
||||
|
||||
/* RGB with black/white points and premult. tables are checked */
|
||||
void curvemapping_evaluate_premulRGBF(CurveMapping *cumap, float vecout[3], const float vecin[3])
|
||||
|
|
|
@ -61,34 +61,39 @@ void ColorCurveOperation::initExecution()
|
|||
void ColorCurveOperation::executePixel(float output[4], float x, float y, PixelSampler sampler)
|
||||
{
|
||||
CurveMapping *cumap = this->m_curveMapping;
|
||||
CurveMapping *workingCopy = (CurveMapping *)MEM_dupallocN(cumap);
|
||||
|
||||
float black[4];
|
||||
float white[4];
|
||||
float fac[4];
|
||||
float image[4];
|
||||
|
||||
/* local versions of cumap->black, cumap->white, cumap->bwmul */
|
||||
float black[4];
|
||||
float white[4];
|
||||
float bwmul[3];
|
||||
|
||||
this->m_inputBlackProgram->read(black, x, y, sampler);
|
||||
this->m_inputWhiteProgram->read(white, x, y, sampler);
|
||||
|
||||
curvemapping_set_black_white(workingCopy, black, white);
|
||||
/* get our own local bwmul value,
|
||||
* since we can't be threadsafe and use cumap->bwmul & friends */
|
||||
curvemapping_set_black_white_ex(black, white, bwmul);
|
||||
|
||||
this->m_inputFacProgram->read(fac, x, y, sampler);
|
||||
this->m_inputImageProgram->read(image, x, y, sampler);
|
||||
|
||||
if (*fac >= 1.0f) {
|
||||
curvemapping_evaluate_premulRGBF(workingCopy, output, image);
|
||||
curvemapping_evaluate_premulRGBF_ex(cumap, output, image,
|
||||
black, bwmul);
|
||||
}
|
||||
else if (*fac <= 0.0f) {
|
||||
copy_v3_v3(output, image);
|
||||
}
|
||||
else {
|
||||
float col[4];
|
||||
curvemapping_evaluate_premulRGBF(workingCopy, col, image);
|
||||
curvemapping_evaluate_premulRGBF_ex(cumap, col, image,
|
||||
black, bwmul);
|
||||
interp_v3_v3v3(output, image, col, *fac);
|
||||
}
|
||||
output[3] = image[3];
|
||||
MEM_freeN(workingCopy);
|
||||
}
|
||||
|
||||
void ColorCurveOperation::deinitExecution()
|
||||
|
|
Loading…
Reference in New Issue