Blur and noise adjustment layers, Image Trim, Inner Glow (12.8c)
This commit is contained in:
1 parent
7ae263de80
commit
31e2dd3864
60 files changed
+1673
-105
No files matched your search
@@ -88,7 +88,8 @@ QImage replayed(const QImage &pixels, const LayerEffects &effects)
|
||||
}
|
||||
const auto on = [](const auto &effect) { return effect && effect->isEnabled() && effect->opacity > 0; };
|
||||
const bool stroke = on(effects.stroke) && effects.stroke->size > 0;
|
||||
std::vector<float> ring(shader.shape.size()), cast(shader.shape.size()), inner(shader.shape.size()), glow(shader.shape.size());
|
||||
std::vector<float> ring(shader.shape.size()), cast(shader.shape.size()), inner(shader.shape.size()), glow(shader.shape.size()),
|
||||
innerGlow(shader.shape.size());
|
||||
if (stroke) {
|
||||
const int reach = std::max(1, int(std::lround(effects.stroke->size)));
|
||||
const std::vector<float> moved = shader.spread(shader.spread(shader.shape, reach, effects.stroke->inside, true), reach, effects.stroke->inside, false);
|
||||
@@ -101,6 +102,12 @@ QImage replayed(const QImage &pixels, const LayerEffects &effects)
|
||||
const bool glowing = on(effects.outerGlow) && effects.outerGlow->size > 0;
|
||||
if (glowing)
|
||||
glow = shader.softened(shader.shape, float(effects.outerGlow->size / 2));
|
||||
const bool glowingInside = on(effects.innerGlow) && effects.innerGlow->size > 0;
|
||||
if (glowingInside) {
|
||||
const std::vector<float> softened = shader.softened(shader.shape, float(effects.innerGlow->size / 2));
|
||||
for (size_t index = 0; index < innerGlow.size(); ++index)
|
||||
innerGlow[index] = std::clamp(shader.shape[index] * (1.f - softened[index]), 0.f, 1.f);
|
||||
}
|
||||
if (on(effects.innerShadow)) {
|
||||
const std::vector<float> moved = shader.softened(shader.shift(shader.shape, float(effects.innerShadow->offset().width()),
|
||||
float(effects.innerShadow->offset().height())),
|
||||
@@ -133,6 +140,8 @@ QImage replayed(const QImage &pixels, const LayerEffects &effects)
|
||||
alpha = sourceAlpha + alpha * (1.f - sourceAlpha);
|
||||
if (on(effects.colorOverlay))
|
||||
blend(effects.colorOverlay->color(), std::clamp(shader.shape[index] * float(effects.colorOverlay->opacity), 0.f, 1.f));
|
||||
if (glowingInside)
|
||||
blend(effects.innerGlow->color(), std::clamp(innerGlow[index] * float(effects.innerGlow->opacity), 0.f, 1.f));
|
||||
if (on(effects.innerShadow))
|
||||
blend(effects.innerShadow->color(), std::clamp(inner[index] * float(effects.innerShadow->opacity), 0.f, 1.f));
|
||||
if (stroke && effects.stroke->inside)
|
||||
@@ -194,7 +203,7 @@ private slots:
|
||||
void LayerEffectsKernelTests::everyEffectMatchesTheShader_data()
|
||||
{
|
||||
QTest::addColumn<LayerEffects>("effects");
|
||||
LayerEffects outside, inside, shadow, overlay, inner, glow, hair, all, wide;
|
||||
LayerEffects outside, inside, shadow, overlay, inner, glow, hair, all, wide, innerGlow, innerHair;
|
||||
outside.stroke = StrokeEffect{.size = 3, .red = 1, .green = 0.5, .blue = 0.25, .opacity = 0.8};
|
||||
inside.stroke = StrokeEffect{.size = 2.5, .red = 0.1, .green = 0.2, .blue = 0.9, .opacity = 1, .inside = true};
|
||||
shadow.shadow = ShadowEffect{.angle = 45, .distance = 3.5, .blur = 4, .red = 0.3, .green = 0.1, .blue = 0.6, .opacity = 0.75};
|
||||
@@ -202,11 +211,14 @@ void LayerEffectsKernelTests::everyEffectMatchesTheShader_data()
|
||||
inner.innerShadow = InnerShadowEffect{.angle = -60, .distance = 2, .blur = 3, .red = 0, .green = 0.4, .blue = 0.2, .opacity = 0.9};
|
||||
glow.outerGlow = OuterGlowEffect{.size = 6, .red = 0.2, .green = 0.9, .blue = 0.4, .opacity = 0.8};
|
||||
hair.outerGlow = OuterGlowEffect{.size = 0.01, .opacity = 1};
|
||||
innerGlow.innerGlow = InnerGlowEffect{.size = 7, .red = 0.8, .green = 0.3, .blue = 0.1, .opacity = 0.7};
|
||||
innerHair.innerGlow = InnerGlowEffect{.size = 0.01, .red = 0, .opacity = 1};
|
||||
all = outside;
|
||||
all.shadow = shadow.shadow;
|
||||
all.colorOverlay = overlay.colorOverlay;
|
||||
all.innerShadow = inner.innerShadow;
|
||||
all.outerGlow = glow.outerGlow;
|
||||
all.innerGlow = innerGlow.innerGlow;
|
||||
all.shadow->blur = 0;
|
||||
wide.stroke = StrokeEffect{.size = 9, .red = 1, .opacity = 1};
|
||||
wide.shadow = ShadowEffect{.angle = 200, .distance = 0.5, .blur = 0.01, .opacity = 1};
|
||||
@@ -217,6 +229,8 @@ void LayerEffectsKernelTests::everyEffectMatchesTheShader_data()
|
||||
QTest::newRow("inner shadow") << inner;
|
||||
QTest::newRow("outer glow") << glow;
|
||||
QTest::newRow("a glow a hair wide") << hair;
|
||||
QTest::newRow("inner glow") << innerGlow;
|
||||
QTest::newRow("an inner glow a hair wide") << innerHair;
|
||||
QTest::newRow("all, a sharp shadow") << all;
|
||||
QTest::newRow("wide stroke, a barely blurred shadow") << wide;
|
||||
}
|
||||
@@ -244,14 +258,17 @@ void LayerEffectsKernelTests::switchedOffOrEmptyEffectsLeaveThePixels()
|
||||
hidden.colorOverlay = ColorOverlayEffect{.enabled = false, .red = 1};
|
||||
hidden.innerShadow = InnerShadowEffect{.enabled = false};
|
||||
hidden.outerGlow = OuterGlowEffect{.enabled = false};
|
||||
LayerEffects dim, flat;
|
||||
hidden.innerGlow = InnerGlowEffect{.enabled = false};
|
||||
LayerEffects dim, flat, dimInside, flatInside;
|
||||
dim.outerGlow = OuterGlowEffect{.opacity = 0};
|
||||
flat.outerGlow = OuterGlowEffect{.size = 0};
|
||||
dimInside.innerGlow = InnerGlowEffect{.opacity = 0};
|
||||
flatInside.innerGlow = InnerGlowEffect{.size = 0};
|
||||
LayerEffects thin;
|
||||
thin.stroke = StrokeEffect{.size = 0, .red = 1};
|
||||
LayerEffects clear;
|
||||
clear.shadow = ShadowEffect{.opacity = 0};
|
||||
for (const LayerEffects &effects : {LayerEffects(), hidden, thin, clear, dim, flat})
|
||||
for (const LayerEffects &effects : {LayerEffects(), hidden, thin, clear, dim, flat, dimInside, flatInside})
|
||||
QCOMPARE(gap(LayerEffectsKernel::render(pixels, effects), pixels), 0);
|
||||
// Stroke sizes round to whole pixels, one at least.
|
||||
LayerEffects fraction, one;
|
||||
|
||||
Reference in new issue
Block a user