https://bugs.kde.org/show_bug.cgi?id=343864

amyspark <a...@amyspark.me> changed:

           What    |Removed                     |Added
----------------------------------------------------------------------------
             Status|ASSIGNED                    |RESOLVED
      Latest Commit|                            |https://invent.kde.org/grap
                   |                            |hics/krita/commit/4cfda40a2
                   |                            |9f9ee7548ab5d2f7320f2fca867
                   |                            |4f65
         Resolution|---                         |FIXED

--- Comment #13 from amyspark <a...@amyspark.me> ---
Git commit 4cfda40a29f9ee7548ab5d2f7320f2fca8674f65 by L. E. Segovia.
Committed on 10/02/2021 at 18:50.
Pushed by lsegovia into branch 'master'.

Feature: HDR gradients

This commit adds suport in Krita for rendering of HDR, high-bit-depth
gradients, and dithering for all output bit depths.

Firstly, all gradient operations are now upgraded; this includes color
mixing ops (step values, upgraded to 16-bit signed integer), and
gradients' default bit depth, which was upgraded to 16-bit integer
or the image's bit depth, whichever is higher.

Secondly, this commit implements a fully SSE+ vectorizable dithering
operator, based on the Pixman low-level graphics library's
implementation (MIT-licensed) available at the following commits:

https://gitlab.freedesktop.org/pixman/pixman/-/commit/ddcc41b999562efdd9f88daa51ffbf39782748b5
https://gitlab.freedesktop.org/pixman/pixman/-/commit/98b5ec74ca14448349ef6a33a663ad19d446ed6b
https://gitlab.freedesktop.org/pixman/pixman/-/commit/cb2ec4268fbde0df3b588ce5cbe2e43e0465452

This version follows closely the original paper of Ulichney's:

Robert A. Ulichney. "Void-and-cluster method for dither array
generation", Proc. SPIE 1913, Human Vision, Visual Processing, and
Digital Display IV, (8 September 1993); doi:10.1117/12.152707

Based on Pixman's work, there are two available options
(but three in code, see below):

- a no-op downsampler

- blue-noise Ulichney's dithering, 64x64, which is the default when
enabled

- Bayer's ordered dithering, 8x8, which has been left as a backup.

The dither operator works by upcasting the pixel to normalized,
floating point color space; applying modulated noise with scale
1 / 2^bit_depth, and then downcasting the pixel to the destination
depth. For obvious reasons, the first step is skipped if the source
is already floating point, and the two latter are no-ops if the
destination's floating point.

The implementation in this commit is structured in a two-level
abstract pattern:

- KisDitherOp is the interface that all operators
expose to dither a single pixel. They are implemented as instances of
KisDitherOpImpl<srcCSTraits, dstCSTraits, DitherType>.

- KisDitherOpImpl is the template class that does the hard work
described above.

Instances of the dither operator are inserted on each colorspace
through a templated, inlined factory function,
addStandardDitherOps<srcCSTraits>(KoColorSpace *). Given the
source bit depth and all known possible destination depths,
this template calls another templated function, addDitherOpsByDepth<
srcCSTraits, dstCSTraits, DitherType>(KoColorSpace *). Each call
to this function creates a KisDitherOpImpl instance corresponding
to each triplet of bit depths and dither implementation, and inserts it
in the given colorspace.

Since this operator needs both source and destination
colorspaces' traits, I check at compilation time that all known traits
have been considered at op creation.

The vectorization properties have been tested with Xcode 11 on macOS,
dumping kritalcmsengine.so with objdump, and checking disassembly
manually.

There are two ways to use this dither operator, once a copy has been
obtained:

- Use dither(const quint8* src, quint8* dst, int x, int y) to dither
a single pixel.

- Use dither(const quint8* src, int srcRowStride, quint8* dst,
int dstRowStride, int x, int y, int columns, int rows) to dither a
whole tile at once. This is the pattern that's used in
KisGradientPainter.

Additionally to Pixman's implementation, and the optimizations already
provided by KoColorSpaceTraits, an optimized version has been
made for the case of pass-through dither and no downcasting, where a
memcpy call suffices.

Finally, this implementation has been made available as a checkbox in:

- the Gradient tool

- Layer / Layer Styles / Gradient overlay

- Fill Layers / Gradient generator

Support has also been included for Photoshop's dithered gradients,
when importing and exporting PSDs. As with the rest of Krita,
they map to blue-noise dithering.

Thanks to Wolthera van Hövell, Dmitry Kazakov, and Mathias Wein for
their review.
CCMAIL: kimages...@kde.org

M  +10   -7    libs/global/kis_global.h
M  +5    -6    libs/image/kis_asl_layer_style_serializer.cpp
M  +73   -20   libs/image/kis_gradient_painter.cc
M  +6    -2    libs/image/kis_gradient_painter.h
M  +3    -1    libs/image/layerstyles/kis_ls_utils.cpp
A  +203  -0    libs/pigment/KisDitherMaths.h     [License: MIT]
A  +52   -0    libs/pigment/KisDitherOp.h     [License: GPL(v2.0+)]
A  +194  -0    libs/pigment/KisDitherOpImpl.h     [License: GPL(v2.0+)]
M  +40   -3    libs/pigment/KoColorSpace.cpp
M  +11   -3    libs/pigment/KoColorSpace.h
M  +2    -2    libs/pigment/KoColorSpaceAbstract.h
M  +5    -1    libs/pigment/KoColorSpace_p.h
M  +3    -1    libs/pigment/colorspaces/KoLabColorSpace.cpp
M  +4    -1    libs/pigment/colorspaces/KoRgbU16ColorSpace.cpp
M  +3    -2    libs/pigment/colorspaces/KoRgbU8ColorSpace.cpp
A  +26   -0    libs/pigment/dithering/KisCmykDitherOpFactory.h     [License:
GPL(v2.0+)]
A  +26   -0    libs/pigment/dithering/KisGrayDitherOpFactory.h     [License:
GPL(v2.0+)]
A  +26   -0    libs/pigment/dithering/KisLabDitherOpFactory.h     [License:
GPL(v2.0+)]
A  +27   -0    libs/pigment/dithering/KisRgbDitherOpFactory.h     [License:
GPL(v2.0+)]
A  +26   -0    libs/pigment/dithering/KisXyzDitherOpFactory.h     [License:
GPL(v2.0+)]
A  +26   -0    libs/pigment/dithering/KisYCbCrDitherOpFactory.h     [License:
GPL(v2.0+)]
M  +40   -67   libs/pigment/resources/KoSegmentGradient.cpp
M  +17   -32   libs/pigment/resources/KoStopGradient.cpp
M  +11   -0    libs/psd/psd.h
M  +3    -0    libs/ui/dialogs/kis_dlg_layer_style.cpp
M  +34   -15   libs/ui/layerstyles/WdgGradientOverlay.ui
M  +3    -1   
plugins/color/lcms2engine/colorspaces/cmyk_f32/CmykF32ColorSpace.cpp
M  +16   -13  
plugins/color/lcms2engine/colorspaces/cmyk_u16/CmykU16ColorSpace.cpp
M  +1    -3   
plugins/color/lcms2engine/colorspaces/cmyk_u16/CmykU16ColorSpace.h
M  +16   -13  
plugins/color/lcms2engine/colorspaces/cmyk_u8/CmykU8ColorSpace.cpp
M  +1    -3    plugins/color/lcms2engine/colorspaces/cmyk_u8/CmykU8ColorSpace.h
M  +3    -0   
plugins/color/lcms2engine/colorspaces/gray_f16/GrayF16ColorSpace.cpp
M  +3    -0   
plugins/color/lcms2engine/colorspaces/gray_f32/GrayF32ColorSpace.cpp
M  +9    -6   
plugins/color/lcms2engine/colorspaces/gray_u16/GrayU16ColorSpace.cpp
M  +1    -3   
plugins/color/lcms2engine/colorspaces/gray_u16/GrayU16ColorSpace.h
M  +9    -6   
plugins/color/lcms2engine/colorspaces/gray_u8/GrayU8ColorSpace.cpp
M  +1    -3    plugins/color/lcms2engine/colorspaces/gray_u8/GrayU8ColorSpace.h
M  +3    -1   
plugins/color/lcms2engine/colorspaces/lab_f32/LabF32ColorSpace.cpp
M  +4    -1    plugins/color/lcms2engine/colorspaces/lab_u16/LabColorSpace.cpp
M  +4    -1    plugins/color/lcms2engine/colorspaces/lab_u8/LabU8ColorSpace.cpp
M  +4    -1   
plugins/color/lcms2engine/colorspaces/rgb_f16/RgbF16ColorSpace.cpp
M  +5    -3   
plugins/color/lcms2engine/colorspaces/rgb_f32/RgbF32ColorSpace.cpp
M  +4    -1   
plugins/color/lcms2engine/colorspaces/rgb_u16/RgbU16ColorSpace.cpp
M  +7    -4    plugins/color/lcms2engine/colorspaces/rgb_u8/RgbU8ColorSpace.cpp
M  +4    -1   
plugins/color/lcms2engine/colorspaces/xyz_f16/XyzF16ColorSpace.cpp
M  +4    -1   
plugins/color/lcms2engine/colorspaces/xyz_f32/XyzF32ColorSpace.cpp
M  +4    -1   
plugins/color/lcms2engine/colorspaces/xyz_u16/XyzU16ColorSpace.cpp
M  +4    -1    plugins/color/lcms2engine/colorspaces/xyz_u8/XyzU8ColorSpace.cpp
M  +4    -1   
plugins/color/lcms2engine/colorspaces/ycbcr_f32/YCbCrF32ColorSpace.cpp
M  +4    -1   
plugins/color/lcms2engine/colorspaces/ycbcr_u16/YCbCrU16ColorSpace.cpp
M  +4    -1   
plugins/color/lcms2engine/colorspaces/ycbcr_u8/YCbCrU8ColorSpace.cpp
M  +3    -1    plugins/generators/gradient/KisGradientGenerator.cpp
M  +4    -0    plugins/generators/gradient/KisGradientGeneratorConfigWidget.cpp
M  +14   -0    plugins/generators/gradient/KisGradientGeneratorConfigWidget.ui
M  +12   -1   
plugins/generators/gradient/KisGradientGeneratorConfiguration.cpp
M  +8    -0    plugins/generators/gradient/KisGradientGeneratorConfiguration.h
M  +17   -2    plugins/tools/basictools/kis_tool_gradient.cc
M  +4    -0    plugins/tools/basictools/kis_tool_gradient.h

https://invent.kde.org/graphics/krita/commit/4cfda40a29f9ee7548ab5d2f7320f2fca8674f65

-- 
You are receiving this mail because:
You are watching all bug changes.

Reply via email to