app: remove premultiplied blending code from the few ops that had it

Change GimpOperationPointLayerMode's "premultiplied" to "linear" and
set format to "RGBA float" if it's TRUE. Everything defaults to FALSE
so nothing changes.
This commit is contained in:
Michael Natterer 2012-12-13 22:58:38 +01:00
parent 0ff07fa385
commit 9b6703371e
7 changed files with 76 additions and 161 deletions

View File

@ -266,7 +266,7 @@ void
gimp_gegl_mode_node_set (GeglNode *node,
GimpLayerModeEffects mode,
gdouble opacity,
gboolean premultiplied)
gboolean linear)
{
const gchar *operation = "gimp:normal-mode";
@ -305,9 +305,9 @@ gimp_gegl_mode_node_set (GeglNode *node,
}
gegl_node_set (node,
"operation", operation,
"opacity", opacity,
"premultiplied", premultiplied,
"operation", operation,
"opacity", opacity,
"linear", linear,
NULL);
}

View File

@ -49,7 +49,7 @@ GeglNode * gimp_gegl_add_buffer_source (GeglNode *parent,
void gimp_gegl_mode_node_set (GeglNode *node,
GimpLayerModeEffects mode,
gdouble opacity,
gboolean premultiplied);
gboolean linear);
void gimp_gegl_node_set_matrix (GeglNode *node,
const GimpMatrix3 *matrix);

View File

@ -83,63 +83,37 @@ gimp_operation_behind_mode_process (GeglOperation *operation,
gfloat *out = out_buf;
const gboolean has_mask = mask != NULL;
if (point->premultiplied)
while (samples--)
{
while (samples--)
gint b;
gdouble value = opacity;
if (has_mask)
value *= *mask;
out[ALPHA] = in[ALPHA] + (1.0 - in[ALPHA]) * layer[ALPHA] * value;
if (out[ALPHA])
{
for (b = RED; b < ALPHA; b++)
{
out[b] = (in[b] * in[ALPHA] + layer[b] * value * layer[ALPHA] * value * (1.0 - in[ALPHA])) / out[ALPHA];
}
}
else
{
gint b;
gdouble value = opacity;
if (has_mask)
value *= *mask;
for (b = RED; b <= ALPHA; b++)
{
out[b] = in[b] + layer[b] * value * (1.0 - in[ALPHA]);
out[b] = in[b];
}
in += 4;
layer += 4;
out += 4;
if (has_mask)
mask++;
}
}
else
{
while (samples--)
{
gint b;
gdouble value = opacity;
if (has_mask)
value *= *mask;
in += 4;
layer += 4;
out += 4;
out[ALPHA] = in[ALPHA] + (1.0 - in[ALPHA]) * layer[ALPHA] * value;
if (out[ALPHA])
{
for (b = RED; b < ALPHA; b++)
{
out[b] = (in[b] * in[ALPHA] + layer[b] * value * layer[ALPHA] * value * (1.0 - in[ALPHA])) / out[ALPHA];
}
}
else
{
for (b = RED; b <= ALPHA; b++)
{
out[b] = in[b];
}
}
in += 4;
layer += 4;
out += 4;
if (has_mask)
mask++;
}
if (has_mask)
mask++;
}
return TRUE;

View File

@ -96,55 +96,27 @@ gimp_operation_erase_mode_process (GeglOperation *operation,
gfloat *out = out_buf;
const gboolean has_mask = mask != NULL;
if (point->premultiplied)
while (samples--)
{
while (samples--)
gint b;
gdouble value = opacity;
if (has_mask)
value *= (*mask);
for (b = RED; b < ALPHA; b++)
{
gint b;
gdouble value = opacity;
if (has_mask)
value *= (*mask);
out[ALPHA] = in[ALPHA] - in[ALPHA] * layer[ALPHA] * value;
for (b = RED; b < ALPHA; b++)
{
out[b] = in[b] / in[ALPHA] * out[ALPHA];
}
in += 4;
layer += 4;
out += 4;
if (has_mask)
mask ++;
out[b] = in[b];
}
}
else
{
while (samples--)
{
gint b;
gdouble value = opacity;
if (has_mask)
value *= (*mask);
out[ALPHA] = in[ALPHA] - in[ALPHA] * layer[ALPHA] * value;
for (b = RED; b < ALPHA; b++)
{
out[b] = in[b];
}
in += 4;
layer += 4;
out += 4;
out[ALPHA] = in[ALPHA] - in[ALPHA] * layer[ALPHA] * value;
in += 4;
layer += 4;
out += 4;
if (has_mask)
mask ++;
}
if (has_mask)
mask ++;
}
return TRUE;

View File

@ -162,72 +162,41 @@ gimp_operation_normal_mode_process (GeglOperation *operation,
gfloat *out = out_buf;
const gboolean has_mask = mask != NULL;
if (point->premultiplied)
while (samples--)
{
while (samples--)
{
gdouble value;
gfloat aux_alpha;
gint b;
gfloat aux_alpha;
value = opacity;
if (has_mask)
value *= *mask;
aux_alpha = aux[ALPHA] * value;
aux_alpha = aux[ALPHA] * opacity;
if (has_mask)
aux_alpha *= *mask;
out[ALPHA] = aux_alpha + in[ALPHA] - aux_alpha * in[ALPHA];
if (out[ALPHA])
{
gint b;
for (b = RED; b < ALPHA; b++)
{
out[b] = aux[b] * value + in[b] * (1.0f - aux_alpha);
out[b] = (aux[b] * aux_alpha + in[b] * in[ALPHA] * (1.0f - aux_alpha)) / out[ALPHA];
}
out[ALPHA] = aux_alpha + in[ALPHA] - aux_alpha * in[ALPHA];
in += 4;
aux += 4;
out += 4;
if (has_mask)
mask++;
}
}
else
{
while (samples--)
else
{
gfloat aux_alpha;
gint b;
aux_alpha = aux[ALPHA] * opacity;
if (has_mask)
aux_alpha *= *mask;
out[ALPHA] = aux_alpha + in[ALPHA] - aux_alpha * in[ALPHA];
if (out[ALPHA])
for (b = RED; b < ALPHA; b++)
{
gint b;
for (b = RED; b < ALPHA; b++)
{
out[b] = (aux[b] * aux_alpha + in[b] * in[ALPHA] * (1.0f - aux_alpha)) / out[ALPHA];
}
out[b] = in[b];
}
else
{
gint b;
for (b = RED; b < ALPHA; b++)
{
out[b] = in[b];
}
}
in += 4;
aux += 4;
out += 4;
if (has_mask)
mask++;
}
in += 4;
aux += 4;
out += 4;
if (has_mask)
mask++;
}
return TRUE;

View File

@ -35,7 +35,7 @@
enum
{
PROP_0,
PROP_PREMULTIPLIED,
PROP_LINEAR,
PROP_OPACITY
};
@ -73,8 +73,8 @@ gimp_operation_point_layer_mode_class_init (GimpOperationPointLayerModeClass *kl
"categories", "compositors",
NULL);
g_object_class_install_property (object_class, PROP_PREMULTIPLIED,
g_param_spec_boolean ("premultiplied",
g_object_class_install_property (object_class, PROP_LINEAR,
g_param_spec_boolean ("linear",
NULL, NULL,
FALSE,
GIMP_PARAM_READWRITE |
@ -103,8 +103,8 @@ gimp_operation_point_layer_mode_set_property (GObject *object,
switch (property_id)
{
case PROP_PREMULTIPLIED:
self->premultiplied = g_value_get_boolean (value);
case PROP_LINEAR:
self->linear = g_value_get_boolean (value);
break;
case PROP_OPACITY:
@ -127,8 +127,8 @@ gimp_operation_point_layer_mode_get_property (GObject *object,
switch (property_id)
{
case PROP_PREMULTIPLIED:
g_value_set_boolean (value, self->premultiplied);
case PROP_LINEAR:
g_value_set_boolean (value, self->linear);
break;
case PROP_OPACITY:
@ -147,8 +147,8 @@ gimp_operation_point_layer_mode_prepare (GeglOperation *operation)
GimpOperationPointLayerMode *self = GIMP_OPERATION_POINT_LAYER_MODE (operation);
const Babl *format;
if (self->premultiplied)
format = babl_format ("R'aG'aB'aA float");
if (self->linear)
format = babl_format ("RGBA float");
else
format = babl_format ("R'G'B'A float");

View File

@ -41,7 +41,7 @@ struct _GimpOperationPointLayerMode
{
GeglOperationPointComposer3 parent_instance;
gboolean premultiplied;
gboolean linear;
gdouble opacity;
};