summaryrefslogtreecommitdiffstats
path: root/src/imports
diff options
context:
space:
mode:
authorEskil Abrahamsen Blomfeldt <eskil.abrahamsen-blomfeldt@qt.io>2021-11-26 08:41:51 +0100
committerEskil Abrahamsen Blomfeldt <eskil.abrahamsen-blomfeldt@qt.io>2022-01-12 12:31:48 +0100
commit0ba059c6dc8b7c0f6ac4a277c96b6b16e43053a2 (patch)
tree0592ca7c110d7bdef7a36c447a3ff155f4c3f367 /src/imports
parent2122920669d09e6a312c566b213c2f12d906fc61 (diff)
Port remaining graphical effects to Qt 6
Brings back shader effects that require runtime generation based on parameters. We use QTemporaryFile to temporarily store generated shaders. This could be made more efficient if we added a way to set the generated shader directly on the shader effect instead. [ChangeLog][GraphicalEffects] Added back missing Qt 5 effects: Blend, DirectionalBlur, DropShadow, GaussianBlur, Glow, InnerShadow, MaskedBlur, RadialBlur, RecursiveBlur, and ZoomBlur. Change-Id: I8ce02a6c8689027258f82dd4fc20bfa39ee6cfea Reviewed-by: Laszlo Agocs <laszlo.agocs@qt.io>
Diffstat (limited to 'src/imports')
-rw-r--r--src/imports/graphicaleffects5/Blend.qml487
-rw-r--r--src/imports/graphicaleffects5/CMakeLists.txt14
-rw-r--r--src/imports/graphicaleffects5/DirectionalBlur.qml298
-rw-r--r--src/imports/graphicaleffects5/DropShadow.qml149
-rw-r--r--src/imports/graphicaleffects5/GaussianBlur.qml375
-rw-r--r--src/imports/graphicaleffects5/Glow.qml126
-rw-r--r--src/imports/graphicaleffects5/InnerShadow.qml386
-rw-r--r--src/imports/graphicaleffects5/MaskedBlur.qml192
-rw-r--r--src/imports/graphicaleffects5/RadialBlur.qml322
-rw-r--r--src/imports/graphicaleffects5/RecursiveBlur.qml329
-rw-r--r--src/imports/graphicaleffects5/ZoomBlur.qml312
-rw-r--r--src/imports/graphicaleffects5/doc/images/Blend_bug_and_butterfly.pngbin0 -> 125749 bytes
-rw-r--r--src/imports/graphicaleffects5/doc/images/Blend_mode1.pngbin0 -> 139179 bytes
-rw-r--r--src/imports/graphicaleffects5/doc/images/Blend_mode10.pngbin0 -> 145578 bytes
-rw-r--r--src/imports/graphicaleffects5/doc/images/Blend_mode11.pngbin0 -> 148982 bytes
-rw-r--r--src/imports/graphicaleffects5/doc/images/Blend_mode12.pngbin0 -> 145855 bytes
-rw-r--r--src/imports/graphicaleffects5/doc/images/Blend_mode13.pngbin0 -> 147901 bytes
-rw-r--r--src/imports/graphicaleffects5/doc/images/Blend_mode14.pngbin0 -> 148626 bytes
-rw-r--r--src/imports/graphicaleffects5/doc/images/Blend_mode15.pngbin0 -> 145787 bytes
-rw-r--r--src/imports/graphicaleffects5/doc/images/Blend_mode16.pngbin0 -> 152469 bytes
-rw-r--r--src/imports/graphicaleffects5/doc/images/Blend_mode17.pngbin0 -> 152450 bytes
-rw-r--r--src/imports/graphicaleffects5/doc/images/Blend_mode18.pngbin0 -> 144022 bytes
-rw-r--r--src/imports/graphicaleffects5/doc/images/Blend_mode19.pngbin0 -> 149328 bytes
-rw-r--r--src/imports/graphicaleffects5/doc/images/Blend_mode2.pngbin0 -> 148805 bytes
-rw-r--r--src/imports/graphicaleffects5/doc/images/Blend_mode20.pngbin0 -> 149488 bytes
-rw-r--r--src/imports/graphicaleffects5/doc/images/Blend_mode21.pngbin0 -> 145464 bytes
-rw-r--r--src/imports/graphicaleffects5/doc/images/Blend_mode22.pngbin0 -> 149514 bytes
-rw-r--r--src/imports/graphicaleffects5/doc/images/Blend_mode3.pngbin0 -> 147745 bytes
-rw-r--r--src/imports/graphicaleffects5/doc/images/Blend_mode4.pngbin0 -> 148132 bytes
-rw-r--r--src/imports/graphicaleffects5/doc/images/Blend_mode5.pngbin0 -> 139048 bytes
-rw-r--r--src/imports/graphicaleffects5/doc/images/Blend_mode6.pngbin0 -> 149569 bytes
-rw-r--r--src/imports/graphicaleffects5/doc/images/Blend_mode7.pngbin0 -> 144323 bytes
-rw-r--r--src/imports/graphicaleffects5/doc/images/Blend_mode8.pngbin0 -> 144640 bytes
-rw-r--r--src/imports/graphicaleffects5/doc/images/Blend_mode9.pngbin0 -> 152549 bytes
-rw-r--r--src/imports/graphicaleffects5/doc/images/DirectionalBlur_angle1.pngbin0 -> 79683 bytes
-rw-r--r--src/imports/graphicaleffects5/doc/images/DirectionalBlur_angle2.pngbin0 -> 87788 bytes
-rw-r--r--src/imports/graphicaleffects5/doc/images/DirectionalBlur_angle3.pngbin0 -> 75902 bytes
-rw-r--r--src/imports/graphicaleffects5/doc/images/DirectionalBlur_bug.pngbin0 -> 72262 bytes
-rw-r--r--src/imports/graphicaleffects5/doc/images/DirectionalBlur_length1.pngbin0 -> 137558 bytes
-rw-r--r--src/imports/graphicaleffects5/doc/images/DirectionalBlur_length2.pngbin0 -> 79683 bytes
-rw-r--r--src/imports/graphicaleffects5/doc/images/DirectionalBlur_length3.pngbin0 -> 79808 bytes
-rw-r--r--src/imports/graphicaleffects5/doc/images/GaussianBlur_bug.pngbin0 -> 85996 bytes
-rw-r--r--src/imports/graphicaleffects5/doc/images/GaussianBlur_deviation1.pngbin0 -> 107188 bytes
-rw-r--r--src/imports/graphicaleffects5/doc/images/GaussianBlur_deviation2.pngbin0 -> 89499 bytes
-rw-r--r--src/imports/graphicaleffects5/doc/images/GaussianBlur_deviation3.pngbin0 -> 73687 bytes
-rw-r--r--src/imports/graphicaleffects5/doc/images/GaussianBlur_deviation4.pngbin0 -> 87436 bytes
-rw-r--r--src/imports/graphicaleffects5/doc/images/GaussianBlur_deviation_graph.pngbin0 -> 9282 bytes
-rw-r--r--src/imports/graphicaleffects5/doc/images/GaussianBlur_radius1.pngbin0 -> 134530 bytes
-rw-r--r--src/imports/graphicaleffects5/doc/images/GaussianBlur_radius2.pngbin0 -> 89842 bytes
-rw-r--r--src/imports/graphicaleffects5/doc/images/GaussianBlur_radius3.pngbin0 -> 79245 bytes
-rw-r--r--src/imports/graphicaleffects5/doc/images/GaussianBlur_transparentBorder1.pngbin0 -> 81884 bytes
-rw-r--r--src/imports/graphicaleffects5/doc/images/GaussianBlur_transparentBorder2.pngbin0 -> 83768 bytes
-rw-r--r--src/imports/graphicaleffects5/doc/images/InnerShadow_butterfly.pngbin0 -> 24735 bytes
-rw-r--r--src/imports/graphicaleffects5/doc/images/InnerShadow_color1.pngbin0 -> 26631 bytes
-rw-r--r--src/imports/graphicaleffects5/doc/images/InnerShadow_color2.pngbin0 -> 26207 bytes
-rw-r--r--src/imports/graphicaleffects5/doc/images/InnerShadow_color3.pngbin0 -> 26885 bytes
-rw-r--r--src/imports/graphicaleffects5/doc/images/InnerShadow_fast1.pngbin0 -> 24516 bytes
-rw-r--r--src/imports/graphicaleffects5/doc/images/InnerShadow_fast2.pngbin0 -> 25208 bytes
-rw-r--r--src/imports/graphicaleffects5/doc/images/InnerShadow_horizontalOffset1.pngbin0 -> 24297 bytes
-rw-r--r--src/imports/graphicaleffects5/doc/images/InnerShadow_horizontalOffset2.pngbin0 -> 24175 bytes
-rw-r--r--src/imports/graphicaleffects5/doc/images/InnerShadow_horizontalOffset3.pngbin0 -> 22163 bytes
-rw-r--r--src/imports/graphicaleffects5/doc/images/InnerShadow_radius1.pngbin0 -> 21336 bytes
-rw-r--r--src/imports/graphicaleffects5/doc/images/InnerShadow_radius2.pngbin0 -> 23283 bytes
-rw-r--r--src/imports/graphicaleffects5/doc/images/InnerShadow_radius3.pngbin0 -> 24046 bytes
-rw-r--r--src/imports/graphicaleffects5/doc/images/InnerShadow_spread1.pngbin0 -> 24175 bytes
-rw-r--r--src/imports/graphicaleffects5/doc/images/InnerShadow_spread2.pngbin0 -> 24662 bytes
-rw-r--r--src/imports/graphicaleffects5/doc/images/InnerShadow_spread3.pngbin0 -> 24982 bytes
-rw-r--r--src/imports/graphicaleffects5/doc/images/MaskedBlur_bug.pngbin0 -> 102774 bytes
-rw-r--r--src/imports/graphicaleffects5/doc/images/MaskedBlur_fast1.pngbin0 -> 108064 bytes
-rw-r--r--src/imports/graphicaleffects5/doc/images/MaskedBlur_fast2.pngbin0 -> 103333 bytes
-rw-r--r--src/imports/graphicaleffects5/doc/images/MaskedBlur_mask.pngbin0 -> 1451 bytes
-rw-r--r--src/imports/graphicaleffects5/doc/images/MaskedBlur_radius1.pngbin0 -> 125113 bytes
-rw-r--r--src/imports/graphicaleffects5/doc/images/MaskedBlur_radius2.pngbin0 -> 113732 bytes
-rw-r--r--src/imports/graphicaleffects5/doc/images/MaskedBlur_radius3.pngbin0 -> 108064 bytes
-rw-r--r--src/imports/graphicaleffects5/doc/images/RadialBlur_angle1.pngbin0 -> 137558 bytes
-rw-r--r--src/imports/graphicaleffects5/doc/images/RadialBlur_angle2.pngbin0 -> 87855 bytes
-rw-r--r--src/imports/graphicaleffects5/doc/images/RadialBlur_angle3.pngbin0 -> 86202 bytes
-rw-r--r--src/imports/graphicaleffects5/doc/images/RadialBlur_bug.pngbin0 -> 80827 bytes
-rw-r--r--src/imports/graphicaleffects5/doc/images/RadialBlur_horizontalOffset1.pngbin0 -> 85352 bytes
-rw-r--r--src/imports/graphicaleffects5/doc/images/RadialBlur_horizontalOffset2.pngbin0 -> 86066 bytes
-rw-r--r--src/imports/graphicaleffects5/doc/images/RadialBlur_horizontalOffset3.pngbin0 -> 87679 bytes
-rw-r--r--src/imports/graphicaleffects5/doc/images/RecursiveBlur_bug.pngbin0 -> 55817 bytes
-rw-r--r--src/imports/graphicaleffects5/doc/images/RecursiveBlur_loops1.pngbin0 -> 60476 bytes
-rw-r--r--src/imports/graphicaleffects5/doc/images/RecursiveBlur_loops2.pngbin0 -> 47842 bytes
-rw-r--r--src/imports/graphicaleffects5/doc/images/RecursiveBlur_loops3.pngbin0 -> 39517 bytes
-rw-r--r--src/imports/graphicaleffects5/doc/images/RecursiveBlur_radius1.pngbin0 -> 67613 bytes
-rw-r--r--src/imports/graphicaleffects5/doc/images/RecursiveBlur_radius2.pngbin0 -> 54404 bytes
-rw-r--r--src/imports/graphicaleffects5/doc/images/RecursiveBlur_radius3.pngbin0 -> 48067 bytes
-rw-r--r--src/imports/graphicaleffects5/doc/images/RecursiveBlur_transparentBorder1.pngbin0 -> 48067 bytes
-rw-r--r--src/imports/graphicaleffects5/doc/images/RecursiveBlur_transparentBorder2.pngbin0 -> 58601 bytes
-rw-r--r--src/imports/graphicaleffects5/doc/images/ZoomBlur_bug.pngbin0 -> 80077 bytes
-rw-r--r--src/imports/graphicaleffects5/doc/images/ZoomBlur_horizontalOffset1.pngbin0 -> 90009 bytes
-rw-r--r--src/imports/graphicaleffects5/doc/images/ZoomBlur_horizontalOffset2.pngbin0 -> 88471 bytes
-rw-r--r--src/imports/graphicaleffects5/doc/images/ZoomBlur_horizontalOffset3.pngbin0 -> 88680 bytes
-rw-r--r--src/imports/graphicaleffects5/doc/images/ZoomBlur_length1.pngbin0 -> 137558 bytes
-rw-r--r--src/imports/graphicaleffects5/doc/images/ZoomBlur_length2.pngbin0 -> 88471 bytes
-rw-r--r--src/imports/graphicaleffects5/doc/images/ZoomBlur_length3.pngbin0 -> 84765 bytes
-rw-r--r--src/imports/graphicaleffects5/doc/snippets/Blend-example.qml74
-rw-r--r--src/imports/graphicaleffects5/doc/snippets/DirectionalBlur-example.qml64
-rw-r--r--src/imports/graphicaleffects5/doc/snippets/GaussianBlur-example.qml63
-rw-r--r--src/imports/graphicaleffects5/doc/snippets/InnerShadow-example.qml70
-rw-r--r--src/imports/graphicaleffects5/doc/snippets/MaskedBlur-example.qml76
-rw-r--r--src/imports/graphicaleffects5/doc/snippets/RadialBlur-example.qml63
-rw-r--r--src/imports/graphicaleffects5/doc/snippets/RecursiveBlur-example.qml63
-rw-r--r--src/imports/graphicaleffects5/doc/snippets/ZoomBlur-example.qml63
-rw-r--r--src/imports/graphicaleffects5/doc/src/overview-graphicaleffects5.qdoc20
-rw-r--r--src/imports/graphicaleffects5/doc/src/qtgraphicaleffects5.qdoc11
-rw-r--r--src/imports/graphicaleffects5/private/CMakeLists.txt9
-rw-r--r--src/imports/graphicaleffects5/private/DropShadowBase.qml98
-rw-r--r--src/imports/graphicaleffects5/private/FastGlow.qml51
-rw-r--r--src/imports/graphicaleffects5/private/FastInnerShadow.qml335
-rw-r--r--src/imports/graphicaleffects5/private/GaussianDirectionalBlur.qml295
-rw-r--r--src/imports/graphicaleffects5/private/GaussianGlow.qml98
-rw-r--r--src/imports/graphicaleffects5/private/GaussianInnerShadow.qml123
-rw-r--r--src/imports/graphicaleffects5/private/GaussianMaskedBlur.qml104
-rw-r--r--src/imports/graphicaleffects5/private/plugin.cpp2
-rw-r--r--src/imports/graphicaleffects5/private/qgfxshaderbuilder.cpp519
-rw-r--r--src/imports/graphicaleffects5/private/qgfxshaderbuilder_p.h77
-rw-r--r--src/imports/graphicaleffects5/private/qgfxsourceproxy.cpp49
-rw-r--r--src/imports/graphicaleffects5/private/qgfxsourceproxy_p.h49
-rw-r--r--src/imports/graphicaleffects5/shaders_ng/compile.bat6
-rw-r--r--src/imports/graphicaleffects5/shaders_ng/fastinnershadow.frag37
-rw-r--r--src/imports/graphicaleffects5/shaders_ng/fastinnershadow.frag.qsbbin0 -> 3125 bytes
-rw-r--r--src/imports/graphicaleffects5/shaders_ng/fastinnershadow_level0.frag20
-rw-r--r--src/imports/graphicaleffects5/shaders_ng/fastinnershadow_level0.frag.qsbbin0 -> 2073 bytes
-rw-r--r--src/imports/graphicaleffects5/shaders_ng/gaussianinnershadow.frag25
-rw-r--r--src/imports/graphicaleffects5/shaders_ng/gaussianinnershadow.frag.qsbbin0 -> 2340 bytes
-rw-r--r--src/imports/graphicaleffects5/shaders_ng/gaussianinnershadow_shadow.frag20
-rw-r--r--src/imports/graphicaleffects5/shaders_ng/gaussianinnershadow_shadow.frag.qsbbin0 -> 2068 bytes
-rw-r--r--src/imports/graphicaleffects5/shaders_ng/recursiveblur.frag16
-rw-r--r--src/imports/graphicaleffects5/shaders_ng/recursiveblur.frag.qsbbin0 -> 1437 bytes
-rw-r--r--src/imports/graphicaleffects5/shaders_ng/recursiveblur.vert22
-rw-r--r--src/imports/graphicaleffects5/shaders_ng/recursiveblur.vert.qsbbin0 -> 2139 bytes
133 files changed, 5312 insertions, 200 deletions
diff --git a/src/imports/graphicaleffects5/Blend.qml b/src/imports/graphicaleffects5/Blend.qml
new file mode 100644
index 0000000..79abf11
--- /dev/null
+++ b/src/imports/graphicaleffects5/Blend.qml
@@ -0,0 +1,487 @@
+/****************************************************************************
+**
+** Copyright (C) 2022 The Qt Company Ltd.
+** Contact: https://www.qt.io/licensing/
+**
+** This file is part of the Qt Graphical Effects module.
+**
+** $QT_BEGIN_LICENSE:LGPL$
+** Commercial License Usage
+** Licensees holding valid commercial Qt licenses may use this file in
+** accordance with the commercial license agreement provided with the
+** Software or, alternatively, in accordance with the terms contained in
+** a written agreement between you and The Qt Company. For licensing terms
+** and conditions see https://www.qt.io/terms-conditions. For further
+** information use the contact form at https://www.qt.io/contact-us.
+**
+** GNU Lesser General Public License Usage
+** Alternatively, this file may be used under the terms of the GNU Lesser
+** General Public License version 3 as published by the Free Software
+** Foundation and appearing in the file LICENSE.LGPL3 included in the
+** packaging of this file. Please review the following information to
+** ensure the GNU Lesser General Public License version 3 requirements
+** will be met: https://www.gnu.org/licenses/lgpl-3.0.html.
+**
+** GNU General Public License Usage
+** Alternatively, this file may be used under the terms of the GNU
+** General Public License version 2.0 or (at your option) the GNU General
+** Public license version 3 or any later version approved by the KDE Free
+** Qt Foundation. The licenses are as published by the Free Software
+** Foundation and appearing in the file LICENSE.GPL2 and LICENSE.GPL3
+** included in the packaging of this file. Please review the following
+** information to ensure the GNU General Public License requirements will
+** be met: https://www.gnu.org/licenses/gpl-2.0.html and
+** https://www.gnu.org/licenses/gpl-3.0.html.
+**
+** $QT_END_LICENSE$
+**
+****************************************************************************/
+
+import QtQuick
+import Qt5Compat.GraphicalEffects.private
+
+/*!
+ \qmltype Blend
+ \inqmlmodule Qt5Compat.GraphicalEffects
+ \since QtGraphicalEffects 1.0
+ \inherits QtQuick2::Item
+ \ingroup qtgraphicaleffects-blend
+ \brief Merges two source items by using a blend mode.
+
+ Blend mode can be selected with the \l{Blend::mode}{mode} property.
+
+ \table
+ \header
+ \li source
+ \li foregroundSource
+ \li Effect applied
+ \row
+ \li \image Original_bug.png
+ \li \image Original_butterfly.png
+ \li \image Blend_bug_and_butterfly.png
+ \endtable
+
+ \note This effect is available when running with OpenGL.
+
+ \section1 Example
+
+ The following example shows how to apply the effect.
+ \snippet Blend-example.qml example
+
+*/
+
+Item {
+ id: rootItem
+
+ /*!
+ This property defines the source item that is going to be the base when
+ \l{Blend::foregroundSource}{foregroundSource} is blended over it.
+
+ \note It is not supported to let the effect include itself, for
+ instance by setting source to the effect's parent.
+ */
+ property variant source
+
+ /*!
+ This property defines the item that is going to be blended over the
+ \l{Blend::source}{source}.
+
+ \note It is not supported to let the effect include itself, for
+ instance by setting foregroundSource to the effect's parent.
+ */
+ property variant foregroundSource
+
+ /*!
+ This property defines the mode which is used when foregroundSource is
+ blended over source. Values are case insensitive.
+
+ \table
+ \header
+ \li mode
+ \li description
+ \row
+ \li normal
+ \li The pixel component values from foregroundSource are written
+ over source by using alpha blending.
+ \row
+ \li addition
+ \li The pixel component values from source and foregroundSource are
+ added together and written.
+ \row
+ \li average
+ \li The pixel component values from source and foregroundSource are
+ averaged and written.
+ \row
+ \li color
+ \li The lightness value from source is combined with hue and
+ saturation from foregroundSource and written.
+ \row
+ \li colorBurn
+ \li The darker pixels from source are darkened more, if both source
+ and foregroundSource pixels are light the result is light.
+ \row
+ \li colorDodge
+ \li The lighter pixels from source are lightened more, if both
+ source and foregroundSource pixels are dark the result is dark.
+ \row
+ \li darken
+ \li The darker pixel component value from source and
+ foregroundSource is written.
+ \row
+ \li darkerColor
+ \li The lower luminance pixel rgb-value from source and
+ foregroundSource is written.
+ \row
+ \li difference
+ \li The absolute pixel component value difference between source and
+ foregroundSource is written.
+ \row
+ \li divide
+ \li The pixel component values from source is divided by the value
+ from foregroundSource and written.
+ \row
+ \li exclusion
+ \li The pixel component value difference with reduced contrast
+ between source and foregroundSource is written.
+ \row
+ \li hardLight
+ \li The pixel component values from source are lightened or darkened
+ according to foregroundSource values and written.
+ \row
+ \li hue
+ \li The hue value from foregroundSource is combined with saturation
+ and lightness from source and written.
+ \row
+ \li lighten
+ \li The lightest pixel component value from source and
+ foregroundSource is written.
+ \row
+ \li lighterColor
+ \li The higher luminance pixel rgb-value from source and
+ foregroundSource is written.
+ \row
+ \li lightness
+ \li The lightness value from foregroundSource is combined with hue
+ and saturation from source and written.
+ \row
+ \li multiply
+ \li The pixel component values from source and foregroundSource are
+ multiplied together and written.
+ \row
+ \li negation
+ \li The inverted absolute pixel component value difference between
+ source and foregroundSource is written.
+ \row
+ \li saturation
+ \li The saturation value from foregroundSource is combined with hue
+ and lightness from source and written.
+ \row
+ \li screen
+ \li The pixel values from source and foregroundSource are negated,
+ then multiplied, negated again, and written.
+ \row
+ \li subtract
+ \li Pixel value from foregroundSource is subracted from source and
+ written.
+ \row
+ \li softLight
+ \li The pixel component values from source are lightened or darkened
+ slightly according to foregroundSource values and written.
+
+ \endtable
+
+ \table
+ \header
+ \li Example source
+ \li Example foregroundSource
+ \row
+ \li \image Original_bug.png
+ \li \image Original_butterfly.png
+ \endtable
+
+ \table
+ \header
+ \li Output examples with different mode values
+ \li
+ \li
+ \row
+ \li \image Blend_mode1.png
+ \li \image Blend_mode2.png
+ \li \image Blend_mode3.png
+ \row
+ \li \b { mode: normal }
+ \li \b { mode: addition }
+ \li \b { mode: average }
+ \row
+ \li \image Blend_mode4.png
+ \li \image Blend_mode5.png
+ \li \image Blend_mode6.png
+ \row
+ \li \b { mode: color }
+ \li \b { mode: colorBurn }
+ \li \b { mode: colorDodge }
+ \row
+ \li \image Blend_mode7.png
+ \li \image Blend_mode8.png
+ \li \image Blend_mode9.png
+ \row
+ \li \b { mode: darken }
+ \li \b { mode: darkerColor }
+ \li \b { mode: difference }
+ \row
+ \li \image Blend_mode10.png
+ \li \image Blend_mode11.png
+ \li \image Blend_mode12.png
+ \row
+ \li \b { mode: divide }
+ \li \b { mode: exclusion }
+ \li \b { mode: hardlight }
+ \row
+ \li \image Blend_mode13.png
+ \li \image Blend_mode14.png
+ \li \image Blend_mode15.png
+ \row
+ \li \b { mode: hue }
+ \li \b { mode: lighten }
+ \li \b { mode: lighterColor }
+ \row
+ \li \image Blend_mode16.png
+ \li \image Blend_mode17.png
+ \li \image Blend_mode18.png
+ \row
+ \li \b { mode: lightness }
+ \li \b { mode: negation }
+ \li \b { mode: multiply }
+ \row
+ \li \image Blend_mode19.png
+ \li \image Blend_mode20.png
+ \li \image Blend_mode21.png
+ \row
+ \li \b { mode: saturation }
+ \li \b { mode: screen }
+ \li \b { mode: subtract }
+ \row
+ \li \image Blend_mode22.png
+ \row
+ \li \b { mode: softLight }
+ \endtable
+ */
+ property string mode: "normal"
+
+ /*!
+ This property allows the effect output pixels to be cached in order to
+ improve the rendering performance.
+
+ Every time the source or effect properties are changed, the pixels in the
+ cache must be updated. Memory consumption is increased, because an extra
+ buffer of memory is required for storing the effect output.
+
+ It is recommended to disable the cache when the source or the effect
+ properties are animated.
+
+ By default, the property is set to false.
+
+ */
+ property bool cached: false
+
+ SourceProxy {
+ id: backgroundSourceProxy
+ input: rootItem.source
+ }
+
+ SourceProxy {
+ id: foregroundSourceProxy
+ input: rootItem.foregroundSource
+ }
+
+ ShaderEffectSource {
+ id: cacheItem
+ anchors.fill: parent
+ visible: rootItem.cached
+ smooth: true
+ sourceItem: shaderItem
+ live: true
+ hideSource: visible
+ }
+
+ ShaderBuilder {
+ id: shaderBuilder
+ }
+
+ ShaderEffect {
+ id: shaderItem
+ property variant source: backgroundSourceProxy.output
+ property variant foregroundSource: foregroundSourceProxy.output
+ property string mode: rootItem.mode
+ anchors.fill: parent
+
+ function buildFragmentShader() {
+ var shader = fragmentShaderBegin
+
+ switch (mode.toLowerCase()) {
+ case "addition" : shader += blendModeAddition; break;
+ case "average" : shader += blendModeAverage; break;
+ case "color" : shader += blendModeColor; break;
+ case "colorburn" : shader += blendModeColorBurn; break;
+ case "colordodge" : shader += blendModeColorDodge; break;
+ case "darken" : shader += blendModeDarken; break;
+ case "darkercolor" : shader += blendModeDarkerColor; break;
+ case "difference" : shader += blendModeDifference; break;
+ case "divide" : shader += blendModeDivide; break;
+ case "exclusion" : shader += blendModeExclusion; break;
+ case "hardlight" : shader += blendModeHardLight; break;
+ case "hue" : shader += blendModeHue; break;
+ case "lighten" : shader += blendModeLighten; break;
+ case "lightercolor" : shader += blendModeLighterColor; break;
+ case "lightness" : shader += blendModeLightness; break;
+ case "negation" : shader += blendModeNegation; break;
+ case "normal" : shader += blendModeNormal; break;
+ case "multiply" : shader += blendModeMultiply; break;
+ case "saturation" : shader += blendModeSaturation; break;
+ case "screen" : shader += blendModeScreen; break;
+ case "subtract" : shader += blendModeSubtract; break;
+ case "softlight" : shader += blendModeSoftLight; break;
+ default: shader += "gl_FragColor = vec4(1.0, 0.0, 0.0, 1.0);"; break;
+ }
+
+ shader += fragmentShaderEnd
+ fragmentShader = shaderBuilder.buildFragmentShader(shader)
+
+ // Workaround for a bug just to make sure display gets updated when the mode changes.
+ sourceChanged()
+ }
+
+ Component.onCompleted: {
+ buildFragmentShader()
+ }
+
+ onModeChanged: {
+ buildFragmentShader()
+ }
+
+ property string blendModeAddition: "result.rgb = min(rgb1 + rgb2, 1.0);"
+ property string blendModeAverage: "result.rgb = 0.5 * (rgb1 + rgb2);"
+ property string blendModeColor: "result.rgb = HSLtoRGB(vec3(RGBtoHSL(rgb2).xy, RGBtoL(rgb1)));"
+ property string blendModeColorBurn: "result.rgb = clamp(1.0 - ((1.0 - rgb1) / max(vec3(1.0 / 256.0), rgb2)), vec3(0.0), vec3(1.0));"
+ property string blendModeColorDodge: "result.rgb = clamp(rgb1 / max(vec3(1.0 / 256.0), (1.0 - rgb2)), vec3(0.0), vec3(1.0));"
+ property string blendModeDarken: "result.rgb = min(rgb1, rgb2);"
+ property string blendModeDarkerColor: "result.rgb = 0.3 * rgb1.r + 0.59 * rgb1.g + 0.11 * rgb1.b > 0.3 * rgb2.r + 0.59 * rgb2.g + 0.11 * rgb2.b ? rgb2 : rgb1;"
+ property string blendModeDifference: "result.rgb = abs(rgb1 - rgb2);"
+ property string blendModeDivide: "result.rgb = clamp(rgb1 / rgb2, 0.0, 1.0);"
+ property string blendModeExclusion: "result.rgb = rgb1 + rgb2 - 2.0 * rgb1 * rgb2;"
+ property string blendModeHardLight: "result.rgb = vec3(channelBlendHardLight(rgb1.r, rgb2.r), channelBlendHardLight(rgb1.g, rgb2.g), channelBlendHardLight(rgb1.b, rgb2.b));"
+ property string blendModeHue: "result.rgb = HSLtoRGB(vec3(RGBtoHSL(rgb2).x, RGBtoHSL(rgb1).yz));"
+ property string blendModeLighten: "result.rgb = max(rgb1, rgb2);"
+ property string blendModeLighterColor: "result.rgb = 0.3 * rgb1.r + 0.59 * rgb1.g + 0.11 * rgb1.b > 0.3 * rgb2.r + 0.59 * rgb2.g + 0.11 * rgb2.b ? rgb1 : rgb2;"
+ property string blendModeLightness: "result.rgb = HSLtoRGB(vec3(RGBtoHSL(rgb1).xy, RGBtoL(rgb2)));"
+ property string blendModeMultiply: "result.rgb = rgb1 * rgb2;"
+ property string blendModeNegation: "result.rgb = 1.0 - abs(1.0 - rgb1 - rgb2);"
+ property string blendModeNormal: "result.rgb = rgb2; a = max(color1.a, color2.a);"
+ property string blendModeSaturation: "vec3 hsl1 = RGBtoHSL(rgb1); result.rgb = HSLtoRGB(vec3(hsl1.x, RGBtoHSL(rgb2).y, hsl1.z));"
+ property string blendModeScreen: "result.rgb = 1.0 - (vec3(1.0) - rgb1) * (vec3(1.0) - rgb2);"
+ property string blendModeSubtract: "result.rgb = max(rgb1 - rgb2, vec3(0.0));"
+ property string blendModeSoftLight: "result.rgb = rgb1 * ((1.0 - rgb1) * rgb2 + (1.0 - (1.0 - rgb1) * (1.0 - rgb2)));"
+
+ property string fragmentShaderBegin: "#version 440
+
+ layout(location = 0) in vec2 qt_TexCoord0;
+ layout(location = 0) out vec4 fragColor;
+
+ layout(std140, binding = 0) uniform buf {
+ mat4 qt_Matrix;
+ float qt_Opacity;
+ };
+ layout(binding = 1) uniform sampler2D source;
+ layout(binding = 2) uniform sampler2D foregroundSource;
+
+ float RGBtoL(vec3 color) {
+ float cmin = min(color.r, min(color.g, color.b));
+ float cmax = max(color.r, max(color.g, color.b));
+ float l = (cmin + cmax) / 2.0;
+ return l;
+ }
+
+ vec3 RGBtoHSL(vec3 color) {
+ float cmin = min(color.r, min(color.g, color.b));
+ float cmax = max(color.r, max(color.g, color.b));
+ float h = 0.0;
+ float s = 0.0;
+ float l = (cmin + cmax) / 2.0;
+ float diff = cmax - cmin;
+
+ if (diff > 1.0 / 256.0) {
+ if (l < 0.5)
+ s = diff / (cmin + cmax);
+ else
+ s = diff / (2.0 - (cmin + cmax));
+
+ if (color.r == cmax)
+ h = (color.g - color.b) / diff;
+ else if (color.g == cmax)
+ h = 2.0 + (color.b - color.r) / diff;
+ else
+ h = 4.0 + (color.r - color.g) / diff;
+
+ h /= 6.0;
+ }
+ return vec3(h, s, l);
+ }
+
+ float hueToIntensity(float v1, float v2, float h) {
+ h = fract(h);
+ if (h < 1.0 / 6.0)
+ return v1 + (v2 - v1) * 6.0 * h;
+ else if (h < 1.0 / 2.0)
+ return v2;
+ else if (h < 2.0 / 3.0)
+ return v1 + (v2 - v1) * 6.0 * (2.0 / 3.0 - h);
+
+ return v1;
+ }
+
+ vec3 HSLtoRGB(vec3 color) {
+ float h = color.x;
+ float l = color.z;
+ float s = color.y;
+
+ if (s < 1.0 / 256.0)
+ return vec3(l, l, l);
+
+ float v1;
+ float v2;
+ if (l < 0.5)
+ v2 = l * (1.0 + s);
+ else
+ v2 = (l + s) - (s * l);
+
+ v1 = 2.0 * l - v2;
+
+ float d = 1.0 / 3.0;
+ float r = hueToIntensity(v1, v2, h + d);
+ float g = hueToIntensity(v1, v2, h);
+ float b = hueToIntensity(v1, v2, h - d);
+ return vec3(r, g, b);
+ }
+
+ float channelBlendHardLight(float c1, float c2) {
+ return c2 > 0.5 ? (1.0 - (1.0 - 2.0 * (c2 - 0.5)) * (1.0 - c1)) : (2.0 * c1 * c2);
+ }
+
+ void main() {
+ vec4 result = vec4(0.0);
+ vec4 color1 = texture(source, qt_TexCoord0);
+ vec4 color2 = texture(foregroundSource, qt_TexCoord0);
+ vec3 rgb1 = color1.rgb / max(1.0/256.0, color1.a);
+ vec3 rgb2 = color2.rgb / max(1.0/256.0, color2.a);
+ float a = max(color1.a, color1.a * color2.a);
+ "
+
+ property string fragmentShaderEnd: "
+ fragColor.rgb = mix(rgb1, result.rgb, color2.a);
+ fragColor.rbg *= a;
+ fragColor.a = a;
+ fragColor *= qt_Opacity;
+ }
+ "
+ }
+}
diff --git a/src/imports/graphicaleffects5/CMakeLists.txt b/src/imports/graphicaleffects5/CMakeLists.txt
index c41570e..ae04dc9 100644
--- a/src/imports/graphicaleffects5/CMakeLists.txt
+++ b/src/imports/graphicaleffects5/CMakeLists.txt
@@ -3,23 +3,31 @@
#####################################################################
set(qml_files
+ "Blend.qml"
"BrightnessContrast.qml"
"ColorOverlay.qml"
"Colorize.qml"
"ConicalGradient.qml"
"Desaturate.qml"
+ "DirectionalBlur.qml"
"Displace.qml"
"DropShadow.qml"
"FastBlur.qml"
"GammaAdjust.qml"
+ "GaussianBlur.qml"
"Glow.qml"
"HueSaturation.qml"
+ "InnerShadow.qml"
"LevelAdjust.qml"
"LinearGradient.qml"
+ "MaskedBlur.qml"
"OpacityMask.qml"
+ "RadialBlur.qml"
"RadialGradient.qml"
"RectangularGlow.qml"
+ "RecursiveBlur.qml"
"ThresholdMask.qml"
+ "ZoomBlur.qml"
)
qt_internal_add_qml_module(qtgraphicaleffectsplugin
@@ -57,8 +65,12 @@ set(qtgraphicaleffectsshaders_resource_files
"shaders_ng/fastblur.frag.qsb"
"shaders_ng/fastblur_internal.frag.qsb"
"shaders_ng/fastblur_internal.vert.qsb"
+ "shaders_ng/fastinnershadow.frag.qsb"
+ "shaders_ng/fastinnershadow_level0.frag.qsb"
"shaders_ng/fastglow.frag.qsb"
"shaders_ng/gammaadjust.frag.qsb"
+ "shaders_ng/gaussianinnershadow.frag.qsb"
+ "shaders_ng/gaussianinnershadow_shadow.frag.qsb"
"shaders_ng/huesaturation.frag.qsb"
"shaders_ng/leveladjust.frag.qsb"
"shaders_ng/lineargradient.vert.qsb"
@@ -69,6 +81,8 @@ set(qtgraphicaleffectsshaders_resource_files
"shaders_ng/radialgradient.vert.qsb"
"shaders_ng/radialgradient_mask.frag.qsb"
"shaders_ng/radialgradient_nomask.frag.qsb"
+ "shaders_ng/recursiveblur.vert.qsb"
+ "shaders_ng/recursiveblur.frag.qsb"
"shaders_ng/rectangularglow.frag.qsb"
"shaders_ng/thresholdmask.frag.qsb"
)
diff --git a/src/imports/graphicaleffects5/DirectionalBlur.qml b/src/imports/graphicaleffects5/DirectionalBlur.qml
new file mode 100644
index 0000000..eec332a
--- /dev/null
+++ b/src/imports/graphicaleffects5/DirectionalBlur.qml
@@ -0,0 +1,298 @@
+/****************************************************************************
+**
+** Copyright (C) 2022 The Qt Company Ltd.
+** Contact: https://www.qt.io/licensing/
+**
+** This file is part of the Qt Graphical Effects module.
+**
+** $QT_BEGIN_LICENSE:LGPL$
+** Commercial License Usage
+** Licensees holding valid commercial Qt licenses may use this file in
+** accordance with the commercial license agreement provided with the
+** Software or, alternatively, in accordance with the terms contained in
+** a written agreement between you and The Qt Company. For licensing terms
+** and conditions see https://www.qt.io/terms-conditions. For further
+** information use the contact form at https://www.qt.io/contact-us.
+**
+** GNU Lesser General Public License Usage
+** Alternatively, this file may be used under the terms of the GNU Lesser
+** General Public License version 3 as published by the Free Software
+** Foundation and appearing in the file LICENSE.LGPL3 included in the
+** packaging of this file. Please review the following information to
+** ensure the GNU Lesser General Public License version 3 requirements
+** will be met: https://www.gnu.org/licenses/lgpl-3.0.html.
+**
+** GNU General Public License Usage
+** Alternatively, this file may be used under the terms of the GNU
+** General Public License version 2.0 or (at your option) the GNU General
+** Public license version 3 or any later version approved by the KDE Free
+** Qt Foundation. The licenses are as published by the Free Software
+** Foundation and appearing in the file LICENSE.GPL2 and LICENSE.GPL3
+** included in the packaging of this file. Please review the following
+** information to ensure the GNU General Public License requirements will
+** be met: https://www.gnu.org/licenses/gpl-2.0.html and
+** https://www.gnu.org/licenses/gpl-3.0.html.
+**
+** $QT_END_LICENSE$
+**
+****************************************************************************/
+
+import QtQuick
+import Qt5Compat.GraphicalEffects.private
+
+/*!
+ \qmltype DirectionalBlur
+ \inqmlmodule Qt5Compat.GraphicalEffects
+ \since QtGraphicalEffects 1.0
+ \inherits QtQuick2::Item
+ \ingroup qtgraphicaleffects-motion-blur
+ \brief Applies blur effect to the specified direction.
+
+ Effect creates perceived impression that the source item appears to be
+ moving in the direction of the blur. Blur is applied to both sides of
+ each pixel, therefore setting the direction to 0 and 180 provides the
+ same result.
+
+ Other available motionblur effects are \l{Qt5Compat.GraphicalEffects::ZoomBlur}{ZoomBlur} and
+ \l{Qt5Compat.GraphicalEffects::RadialBlur}{RadialBlur}.
+
+ \table
+ \header
+ \li Source
+ \li Effect applied
+ \row
+ \li \image Original_bug.png
+ \li \image DirectionalBlur_bug.png
+ \endtable
+
+ \note This effect is available when running with OpenGL.
+
+ \section1 Example
+
+ The following example shows how to apply the effect.
+ \snippet DirectionalBlur-example.qml example
+
+*/
+Item {
+ id: rootItem
+
+ /*!
+ This property defines the source item that is going to be blurred.
+
+ \note It is not supported to let the effect include itself, for
+ instance by setting source to the effect's parent.
+ */
+ property variant source
+
+ /*!
+ This property defines the perceived amount of movement for each pixel.
+ The movement is divided evenly to both sides of each pixel.
+
+ The quality of the blur depends on \l{DirectionalBlur::samples}{samples}
+ property. If length value is large, more samples are needed to keep the
+ visual quality at high level.
+
+ The value ranges from 0.0 to inf.
+ By default the property is set to \c 0.0 (no blur).
+
+ \table
+ \header
+ \li Output examples with different length values
+ \li
+ \li
+ \row
+ \li \image DirectionalBlur_length1.png
+ \li \image DirectionalBlur_length2.png
+ \li \image DirectionalBlur_length3.png
+ \row
+ \li \b { length: 0.0 }
+ \li \b { length: 32.0 }
+ \li \b { length: 48.0 }
+ \row
+ \li \l samples: 24
+ \li \l samples: 24
+ \li \l samples: 24
+ \row
+ \li \l angle: 0
+ \li \l angle: 0
+ \li \l angle: 0
+ \endtable
+
+ */
+ property real length: 0.0
+
+ /*!
+ This property defines how many samples are taken per pixel when blur
+ calculation is done. Larger value produces better quality, but is slower
+ to render.
+
+ This property is not intended to be animated. Changing this property may
+ cause the underlying OpenGL shaders to be recompiled.
+
+ Allowed values are between 0 and inf (practical maximum depends on GPU).
+ By default the property is set to \c 0 (no samples).
+
+ */
+ property int samples: 0
+
+ /*!
+ This property defines the direction for the blur. Blur is applied to
+ both sides of each pixel, therefore setting the direction to 0 and 180
+ produces the same result.
+
+ The value ranges from -180.0 to 180.0.
+ By default the property is set to \c 0.0.
+
+ \table
+ \header
+ \li Output examples with different angle values
+ \li
+ \li
+ \row
+ \li \image DirectionalBlur_angle1.png
+ \li \image DirectionalBlur_angle2.png
+ \li \image DirectionalBlur_angle3.png
+ \row
+ \li \b { angle: 0.0 }
+ \li \b { angle: 45.0 }
+ \li \b { angle: 90.0 }
+ \row
+ \li \l samples: 24
+ \li \l samples: 24
+ \li \l samples: 24
+ \row
+ \li \l length: 32
+ \li \l length: 32
+ \li \l length: 32
+ \endtable
+
+ */
+ property real angle: 0.0
+
+ /*!
+ This property defines the blur behavior near the edges of the item,
+ where the pixel blurring is affected by the pixels outside the source
+ edges.
+
+ If the property is set to \c true, the pixels outside the source are
+ interpreted to be transparent, which is similar to OpenGL
+ clamp-to-border extension. The blur is expanded slightly outside the
+ effect item area.
+
+ If the property is set to \c false, the pixels outside the source are
+ interpreted to contain the same color as the pixels at the edge of the
+ item, which is similar to OpenGL clamp-to-edge behavior. The blur does
+ not expand outside the effect item area.
+
+ By default, the property is set to \c false.
+
+ */
+ property bool transparentBorder: false
+
+ /*!
+ This property allows the effect output pixels to be cached in order to
+ improve the rendering performance.
+
+ Every time the source or effect properties are changed, the pixels in
+ the cache must be updated. Memory consumption is increased, because an
+ extra buffer of memory is required for storing the effect output.
+
+ It is recommended to disable the cache when the source or the effect
+ properties are animated.
+
+ By default, the property is set to \c false.
+
+ */
+ property bool cached: false
+
+ SourceProxy {
+ id: sourceProxy
+ input: rootItem.source
+ sourceRect: rootItem.transparentBorder ? Qt.rect(-1, -1, parent.width + 2.0, parent.height + 2.0) : Qt.rect(0, 0, 0, 0)
+ }
+
+ ShaderEffectSource {
+ id: cacheItem
+ anchors.fill: shaderItem
+ visible: rootItem.cached
+ smooth: true
+ sourceItem: shaderItem
+ live: true
+ hideSource: visible
+ }
+
+ ShaderBuilder {
+ id: shaderBuilder
+ }
+
+ ShaderEffect {
+ id: shaderItem
+ property variant source: sourceProxy.output
+ property real len: rootItem.length
+ property bool transparentBorder: rootItem.transparentBorder
+ property real samples: rootItem.samples
+ property real weight: 1.0 / Math.max(1.0, rootItem.samples)
+ property variant expandPixels: transparentBorder ? Qt.size(rootItem.samples, rootItem.samples) : Qt.size(0,0)
+ property variant expand: transparentBorder ? Qt.size(expandPixels.width / width, expandPixels.height / height) : Qt.size(0,0)
+ property variant delta: Qt.size(1.0 / rootItem.width * Math.cos((rootItem.angle + 90) * Math.PI/180), 1.0 / rootItem.height * Math.sin((rootItem.angle + 90) * Math.PI/180))
+
+ x: transparentBorder ? -expandPixels.width - 1: 0
+ y: transparentBorder ? -expandPixels.height - 1 : 0
+ width: transparentBorder ? parent.width + 2.0 * expandPixels.width + 2 : parent.width
+ height: transparentBorder ? parent.height + 2.0 * expandPixels.height + 2 : parent.height
+
+ property string fragmentShaderSkeleton: "#version 440
+ layout(location = 0) in vec2 qt_TexCoord0;
+ layout(location = 0) out vec4 fragColor;
+ layout(std140, binding = 0) uniform buf {
+ mat4 qt_Matrix;
+ float qt_Opacity;
+ float len;
+ float samples;
+ float weight;
+ vec2 expand;
+ vec2 delta;
+ };
+ layout(binding = 1) uniform sampler2D source;
+
+ void main(void) {
+ vec2 shift = delta * len / max(1.0, samples - 1.0);
+ vec2 texCoord = qt_TexCoord0;
+ fragColor = vec4(0.0);
+
+ PLACEHOLDER_EXPAND_STEPS
+
+ texCoord -= shift * max(0.0, samples - 1.0) * 0.5;
+
+ PLACEHOLDER_UNROLLED_LOOP
+
+ fragColor *= weight * qt_Opacity;
+ }
+ "
+
+ function buildFragmentShader() {
+ var shader = fragmentShaderSkeleton
+ var expandSteps = ""
+
+ if (transparentBorder) {
+ expandSteps += "texCoord = (texCoord - expand) / (1.0 - 2.0 * expand);"
+ }
+
+ var unrolledLoop = "fragColor += texture(source, texCoord);\n"
+
+ if (rootItem.samples > 1) {
+ unrolledLoop = ""
+ for (var i = 0; i < rootItem.samples; i++)
+ unrolledLoop += "fragColor += texture(source, texCoord); texCoord += shift;\n"
+ }
+
+ shader = shader.replace("PLACEHOLDER_EXPAND_STEPS", expandSteps)
+ fragmentShader = shaderBuilder.buildFragmentShader(shader.replace("PLACEHOLDER_UNROLLED_LOOP", unrolledLoop))
+ }
+
+ onFragmentShaderChanged: sourceChanged()
+ onSamplesChanged: buildFragmentShader()
+ onTransparentBorderChanged: buildFragmentShader()
+ Component.onCompleted: buildFragmentShader()
+ }
+}
diff --git a/src/imports/graphicaleffects5/DropShadow.qml b/src/imports/graphicaleffects5/DropShadow.qml
index 60eefcb..66554ca 100644
--- a/src/imports/graphicaleffects5/DropShadow.qml
+++ b/src/imports/graphicaleffects5/DropShadow.qml
@@ -58,9 +58,14 @@ import Qt5Compat.GraphicalEffects.private
\since QtGraphicalEffects 1.0
\inherits QtQuick2::Item
\ingroup qtgraphicaleffects-drop-shadow
- \brief Generates a colorized and blurred shadow image of the
- source and places it behind the original, giving the impression that
- source item is raised from the background.
+
+ \brief Generates a soft shadow behind the source item.
+
+ The DropShadow effect blurs the alpha channel of the input, colorizes the
+ result and places it behind the source object to create a soft shadow. The
+ shadow's color can be changed using the \l {DropShadow::color}{color}
+ property. The location of the shadow can be changed with the \l
+ horizontalOffset and \l verticalOffset properties.
\table
\header
@@ -71,6 +76,16 @@ import Qt5Compat.GraphicalEffects.private
\li \image DropShadow_butterfly.png
\endtable
+ The soft shadow is created by blurring the image live using a gaussian
+ blur. Performing blur live is a costly operation. Fullscreen gaussian blur
+ with even a moderate number of samples will only run at 60 fps on highend
+ graphics hardware.
+
+ When the source is static, the \l cached property can be set to allocate
+ another buffer to avoid performing the blur every time it is drawn.
+
+ \note This effect is available when running with OpenGL.
+
\section1 Example
The following example shows how to apply the effect.
@@ -78,7 +93,12 @@ import Qt5Compat.GraphicalEffects.private
*/
Item {
- id: rootItem
+ id: root
+
+ DropShadowBase {
+ id: dbs
+ anchors.fill: parent
+ }
/*!
This property defines the source item that is going to be used as the
@@ -87,14 +107,26 @@ Item {
\note It is not supported to let the effect include itself, for
instance by setting source to the effect's parent.
*/
- property variant source
+ property alias source: dbs.source
/*!
+ \qmlproperty int DropShadow::radius
+
Radius defines the softness of the shadow. A larger radius causes the
edges of the shadow to appear more blurry.
- The value ranges from 0.0 (no blur) to inf. By default, the property is
- set to \c 0.0 (no blur).
+ The ideal blur is achieved by selecting \c samples and \c radius such
+ that \c {samples = 1 + radius * 2}, such as:
+
+ \table
+ \header \li Radius \li Samples
+ \row \li 0 \e{(no blur)} \li 1
+ \row \li 1 \li 3
+ \row \li 2 \li 5
+ \row \li 3 \li 7
+ \endtable
+
+ By default, the property is set to \c {floor(samples/2)}.
\table
\header
@@ -110,6 +142,10 @@ Item {
\li \b { radius: 6 }
\li \b { radius: 12 }
\row
+ \li \l samples: 25
+ \li \l samples: 25
+ \li \l samples: 25
+ \row
\li \l color: #000000
\li \l color: #000000
\li \l color: #000000
@@ -126,9 +162,31 @@ Item {
\li \l spread: 0
\li \l spread: 0
\endtable
+ */
+ property alias radius: dbs.radius;
+
+ /*!
+ This property defines how many samples are taken per pixel when edge
+ softening blur calculation is done. Larger value produces better
+ quality, but is slower to render.
+
+ Ideally, this value should be twice as large as the highest required
+ radius value plus one, such as:
+
+ \table
+ \header \li Radius \li Samples
+ \row \li 0 \e{(no blur)} \li 1
+ \row \li 1 \li 3
+ \row \li 2 \li 5
+ \row \li 3 \li 7
+ \endtable
+
+ By default, the property is set to \c 9.
+ This property is not intended to be animated. Changing this property will
+ cause the underlying OpenGL shaders to be recompiled.
*/
- property real radius: 0.0
+ property alias samples: dbs.samples
/*!
This property defines the RGBA color value which is used for the shadow.
@@ -153,6 +211,10 @@ Item {
\li \l radius: 8
\li \l radius: 8
\row
+ \li \l samples: 17
+ \li \l samples: 17
+ \li \l samples: 17
+ \row
\li \l horizontalOffset: 0
\li \l horizontalOffset: 0
\li \l horizontalOffset: 0
@@ -165,9 +227,8 @@ Item {
\li \l spread: 0
\li \l spread: 0
\endtable
-
*/
- property color color: "black"
+ property alias color: dbs.color
/*!
\qmlproperty real QtGraphicalEffects::DropShadow::horizontalOffset
@@ -202,6 +263,10 @@ Item {
\li \l radius: 4
\li \l radius: 4
\row
+ \li \l samples: 9
+ \li \l samples: 9
+ \li \l samples: 9
+ \row
\li \l color: #000000
\li \l color: #000000
\li \l color: #000000
@@ -214,17 +279,16 @@ Item {
\li \l spread: 0
\li \l spread: 0
\endtable
-
*/
- property real horizontalOffset: 0.0
- property real verticalOffset: 0.0
+ property alias horizontalOffset: dbs.horizontalOffset
+ property alias verticalOffset: dbs.verticalOffset
/*!
- This property defines how large part of the shadow color is strenghtened
+ This property defines how large part of the shadow color is strengthened
near the source edges.
The value ranges from 0.0 to 1.0. By default, the property is set to \c
- 0.5.
+ 0.0.
\table
\header
@@ -244,6 +308,10 @@ Item {
\li \l radius: 8
\li \l radius: 8
\row
+ \li \l samples: 17
+ \li \l samples: 17
+ \li \l samples: 17
+ \row
\li \l color: #000000
\li \l color: #000000
\li \l color: #000000
@@ -256,9 +324,18 @@ Item {
\li \l verticalOffset: 20
\li \l verticalOffset: 20
\endtable
+ */
+ property alias spread: dbs.spread
+
+ /*!
+ \internal
+ Starting Qt 5.6, this property has no effect. It is left here
+ for source compatibility only.
+
+ ### Qt 6: remove
*/
- property real spread: 0.0
+ property bool fast: false
/*!
This property allows the effect output pixels to be cached in order to
@@ -271,9 +348,8 @@ Item {
properties are animated.
By default, the property is set to \c false.
-
*/
- property bool cached: false
+ property alias cached: dbs.cached
/*!
This property determines whether or not the effect has a transparent
@@ -282,45 +358,16 @@ Item {
When set to \c true, the exterior of the item is padded with a 1 pixel
wide transparent edge, making sampling outside the source texture use
transparency instead of the edge pixels. Without this property, an
- image which has opaque edges will not get a blurred edge.
+ image which has opaque edges will not get a blurred shadow.
In the image below, the Rectangle on the left has transparent borders
and has blurred edges, whereas the Rectangle on the right does not:
+ By default, this property is set to \c true.
+
\snippet DropShadow-transparentBorder-example.qml example
\image DropShadow-transparentBorder.png
*/
- property bool transparentBorder: false
-
- Loader {
- x: rootItem.horizontalOffset
- y: rootItem.verticalOffset
- width: parent.width
- height: parent.height
- sourceComponent: fastGlow
- }
-
- Component {
- id: fastGlow
- FastGlow {
- anchors.fill: parent
- source: sourceProxy.output
- blur: Math.pow(rootItem.radius / 64.0, 0.4)
- color: rootItem.color
- cached: rootItem.cached
- spread: rootItem.spread
- transparentBorder: rootItem.transparentBorder
- }
- }
-
- SourceProxy {
- id: sourceProxy
- input: rootItem.source
- sourceRect: rootItem.transparentBorder ? Qt.rect(-1, -1, parent.width + 2.0, parent.height + 2.0) : Qt.rect(0, 0, 0, 0)
- }
- ShaderEffect {
- anchors.fill: parent
- property variant source: sourceProxy.output
- }
+ property alias transparentBorder: dbs.transparentBorder
}
diff --git a/src/imports/graphicaleffects5/GaussianBlur.qml b/src/imports/graphicaleffects5/GaussianBlur.qml
new file mode 100644
index 0000000..87cdae1
--- /dev/null
+++ b/src/imports/graphicaleffects5/GaussianBlur.qml
@@ -0,0 +1,375 @@
+/****************************************************************************
+**
+** Copyright (C) 2017 The Qt Company Ltd.
+** Copyright (C) 2017 Jolla Ltd, author: <gunnar.sletta@jollamobile.com>
+** Contact: https://www.qt.io/licensing/
+**
+** This file is part of the Qt Graphical Effects module.
+**
+** $QT_BEGIN_LICENSE:LGPL$
+** Commercial License Usage
+** Licensees holding valid commercial Qt licenses may use this file in
+** accordance with the commercial license agreement provided with the
+** Software or, alternatively, in accordance with the terms contained in
+** a written agreement between you and The Qt Company. For licensing terms
+** and conditions see https://www.qt.io/terms-conditions. For further
+** information use the contact form at https://www.qt.io/contact-us.
+**
+** GNU Lesser General Public License Usage
+** Alternatively, this file may be used under the terms of the GNU Lesser
+** General Public License version 3 as published by the Free Software
+** Foundation and appearing in the file LICENSE.LGPL3 included in the
+** packaging of this file. Please review the following information to
+** ensure the GNU Lesser General Public License version 3 requirements
+** will be met: https://www.gnu.org/licenses/lgpl-3.0.html.
+**
+** GNU General Public License Usage
+** Alternatively, this file may be used under the terms of the GNU
+** General Public License version 2.0 or (at your option) the GNU General
+** Public license version 3 or any later version approved by the KDE Free
+** Qt Foundation. The licenses are as published by the Free Software
+** Foundation and appearing in the file LICENSE.GPL2 and LICENSE.GPL3
+** included in the packaging of this file. Please review the following
+** information to ensure the GNU General Public License requirements will
+** be met: https://www.gnu.org/licenses/gpl-2.0.html and
+** https://www.gnu.org/licenses/gpl-3.0.html.
+**
+** $QT_END_LICENSE$
+**
+****************************************************************************/
+
+import QtQuick
+import QtQuick.Window
+import Qt5Compat.GraphicalEffects.private
+
+/*!
+ \qmltype GaussianBlur
+ \inqmlmodule Qt5Compat.GraphicalEffects
+ \since QtGraphicalEffects 1.0
+ \inherits QtQuick2::Item
+ \ingroup qtgraphicaleffects-blur
+ \brief Applies a higher quality blur effect.
+
+ GaussianBlur effect softens the image by blurring it with an algorithm that
+ uses the Gaussian function to calculate the effect. The effect produces
+ higher quality than \l{Qt5Compat.GraphicalEffects::FastBlur}{FastBlur}, but is
+ slower to render.
+
+ \table
+ \header
+ \li Source
+ \li Effect applied
+ \row
+ \li \image Original_bug.png
+ \li \image GaussianBlur_bug.png
+ \endtable
+
+ \note This effect is available when running with OpenGL.
+
+ \section1 Example
+
+ The following example shows how to apply the effect.
+ \snippet GaussianBlur-example.qml example
+
+ Performing blur live is a costly operation. Fullscreen gaussian blur
+ with even a moderate number of samples will only run at 60 fps on highend
+ graphics hardware.
+*/
+Item {
+ id: root
+
+ /*!
+ This property defines the source item that is going to be blurred.
+
+ \note It is not supported to let the effect include itself, for
+ instance by setting source to the effect's parent.
+ */
+ property variant source
+
+ /*!
+ This property defines the distance of the neighboring pixels which
+ affect the blurring of an individual pixel. A larger radius increases
+ the blur effect.
+
+ The ideal blur is achieved by selecting \c samples and \c radius such
+ that \c {samples = 1 + radius * 2}, such as:
+
+ \table
+ \header \li Radius \li Samples
+ \row \li 0 \e{(no blur)} \li 1
+ \row \li 1 \li 3
+ \row \li 2 \li 5
+ \row \li 3 \li 7
+ \endtable
+
+ The value ranges from 0.0 (no blur) to inf. By default, the property is
+ set to \c floor(samples / 2.0).
+
+ \table
+ \header
+ \li Output examples with different radius values
+ \li
+ \li
+ \row
+ \li \image GaussianBlur_radius1.png
+ \li \image GaussianBlur_radius2.png
+ \li \image GaussianBlur_radius3.png
+ \row
+ \li \b { radius: 0 }
+ \li \b { radius: 4 }
+ \li \b { radius: 8 }
+ \row
+ \li \l samples: 16
+ \li \l samples: 16
+ \li \l samples: 16
+ \row
+ \li \l deviation: 3
+ \li \l deviation: 3
+ \li \l deviation: 3
+ \endtable
+
+ */
+ property real radius: Math.floor(samples / 2);
+
+ /*!
+ This property defines how many samples are taken per pixel when blur
+ calculation is done. Larger value produces better quality, but is slower
+ to render.
+
+ Ideally, this value should be twice as large as the highest required
+ radius value plus 1, for example, if the radius is animated between 0.0
+ and 4.0, samples should be set to 9.
+
+ By default, the property is set to \c 9.
+
+ \note This property is not intended to be animated. Changing this property may
+ cause the underlying OpenGL shaders to be recompiled.
+
+ */
+ property int samples: 9
+
+ /*!
+ This property is a parameter to the gaussian function that is used when
+ calculating neighboring pixel weights for the blurring. A larger
+ deviation causes image to appear more blurry, but it also reduces the
+ quality of the blur. A very large deviation value causes the effect to
+ look a bit similar to what, for exmple, a box blur algorithm produces. A
+ too small deviation values makes the effect insignificant for the pixels
+ near the radius.
+
+ \inlineimage GaussianBlur_deviation_graph.png
+ \caption The image above shows the Gaussian function with two different
+ deviation values, yellow (1) and cyan (2.7). The y-axis shows the
+ weights, the x-axis shows the pixel distance.
+
+ The value ranges from 0.0 (no deviation) to inf (maximum deviation). By
+ default, devaition is binded to radius. When radius increases, deviation
+ is automatically increased linearly. With the radius value of 8, the
+ deviation default value becomes approximately 2.7034. This value
+ produces a compromise between the blur quality and overall blurriness.
+
+ \table
+ \header
+ \li Output examples with different deviation values
+ \li
+ \li
+ \row
+ \li \image GaussianBlur_deviation1.png
+ \li \image GaussianBlur_deviation2.png
+ \li \image GaussianBlur_deviation3.png
+ \row
+ \li \b { deviation: 1 }
+ \li \b { deviation: 2 }
+ \li \b { deviation: 4 }
+ \row
+ \li \l radius: 8
+ \li \l radius: 8
+ \li \l radius: 8
+ \row
+ \li \l samples: 16
+ \li \l samples: 16
+ \li \l samples: 16
+ \endtable
+
+ */
+ property real deviation: (radius + 1.0) / 3.3333
+
+ /*!
+ This property defines the blur behavior near the edges of the item,
+ where the pixel blurring is affected by the pixels outside the source
+ edges.
+
+ If the property is set to \c true, the pixels outside the source are
+ interpreted to be transparent, which is similar to OpenGL
+ clamp-to-border extension. The blur is expanded slightly outside the
+ effect item area.
+
+ If the property is set to \c false, the pixels outside the source are
+ interpreted to contain the same color as the pixels at the edge of the
+ item, which is similar to OpenGL clamp-to-edge behavior. The blur does
+ not expand outside the effect item area.
+
+ By default, the property is set to \c false.
+
+ \table
+ \header
+ \li Output examples with different transparentBorder values
+ \li
+ \li
+ \row
+ \li \image GaussianBlur_transparentBorder1.png
+ \li \image GaussianBlur_transparentBorder2.png
+ \row
+ \li \b { transparentBorder: false }
+ \li \b { transparentBorder: true }
+ \row
+ \li \l radius: 8
+ \li \l radius: 8
+ \row
+ \li \l samples: 16
+ \li \l samples: 16
+ \row
+ \li \l deviation: 2.7
+ \li \l deviation: 2.7
+ \endtable
+ */
+ property bool transparentBorder: false
+
+ /*!
+ This property allows the effect output pixels to be cached in order to
+ improve the rendering performance.
+ Every time the source or effect properties are changed, the pixels in
+ the cache must be updated. Memory consumption is increased, because an
+ extra buffer of memory is required for storing the effect output.
+
+ It is recommended to disable the cache when the source or the effect
+ properties are animated.
+
+ By default, the property is set to \c false.
+
+ */
+ property bool cached: false
+
+
+ // private members...
+ /*! \internal */
+ property int _paddedTexWidth: transparentBorder ? width + 2 * radius: width;
+ /*! \internal */
+ property int _paddedTexHeight: transparentBorder ? height + 2 * radius: height;
+ /*! \internal */
+ property int _kernelRadius: Math.max(0, samples / 2);
+ /*! \internal */
+ property int _kernelSize: _kernelRadius * 2 + 1;
+ /*! \internal */
+ property real _dpr: Screen.devicePixelRatio;
+ /*! \internal */
+ property bool _alphaOnly: false;
+ /*! \internal */
+ property var _maskSource: undefined
+
+ /*! \internal */
+ property alias _output: sourceProxy.output;
+ /*! \internal */
+ property alias _outputRect: sourceProxy.sourceRect;
+ /*! \internal */
+ property alias _color: verticalBlur.color;
+ /*! \internal */
+ property real _thickness: 0;
+
+ onSamplesChanged: _rebuildShaders();
+ on_KernelSizeChanged: _rebuildShaders();
+ onDeviationChanged: _rebuildShaders();
+ on_DprChanged: _rebuildShaders();
+ on_MaskSourceChanged: _rebuildShaders();
+ Component.onCompleted: _rebuildShaders();
+
+ ShaderBuilder {
+ id: shaderBuilder
+ }
+
+ /*! \internal */
+ function _rebuildShaders() {
+ var params = {
+ radius: _kernelRadius,
+ // Limit deviation to something very small avoid getting NaN in the shader.
+ deviation: Math.max(0.00001, deviation),
+ alphaOnly: root._alphaOnly,
+ masked: _maskSource != undefined,
+ fallback: root.radius != _kernelRadius
+ }
+ var shaders = shaderBuilder.gaussianBlur(params);
+ horizontalBlur.fragmentShader = shaders.fragmentShader;
+ horizontalBlur.vertexShader = shaders.vertexShader;
+ }
+
+ SourceProxy {
+ id: sourceProxy
+ interpolation: SourceProxy.LinearInterpolation
+ input: root.source
+ sourceRect: root.transparentBorder
+ ? Qt.rect(-root.radius, 0, root._paddedTexWidth, parent.height)
+ : Qt.rect(0, 0, 0, 0)
+ }
+
+ ShaderEffect {
+ id: horizontalBlur
+ width: root.transparentBorder ? root._paddedTexWidth : root.width
+ height: root.height;
+
+ // Used by all shaders
+ property Item source: sourceProxy.output;
+ property real spread: root.radius / root._kernelRadius;
+ property var dirstep: Qt.vector2d(1 / (root._paddedTexWidth * root._dpr), 0);
+
+ // Used by fallback shader (sampleCount exceeds number of varyings)
+ property real deviation: root.deviation
+
+ // Only in use for DropShadow and Glow
+ property color color: "white"
+ property real thickness: Math.max(0, Math.min(0.98, 1 - root._thickness * 0.98));
+
+ // Only in use for MaskedBlur
+ property var mask: root._maskSource;
+
+ layer.enabled: true
+ layer.smooth: true
+ layer.sourceRect: root.transparentBorder
+ ? Qt.rect(0, -root.radius, width, root._paddedTexHeight)
+ : Qt.rect(0, 0, 0, 0)
+ visible: false
+ blending: false
+ }
+
+ ShaderEffect {
+ id: verticalBlur
+ x: transparentBorder ? -root.radius : 0
+ y: x;
+ width: root.transparentBorder ? root._paddedTexWidth: root.width
+ height: root.transparentBorder ? root._paddedTexHeight : root.height;
+ fragmentShader: horizontalBlur.fragmentShader
+ vertexShader: horizontalBlur.vertexShader
+
+ property Item source: horizontalBlur
+ property real spread: horizontalBlur.spread
+ property var dirstep: Qt.vector2d(0, 1 / (root._paddedTexHeight * root._dpr));
+
+ property real deviation: horizontalBlur.deviation
+
+ property color color: "black"
+ property real thickness: horizontalBlur.thickness;
+
+ property var mask: horizontalBlur.mask;
+
+ visible: true
+ }
+
+ ShaderEffectSource {
+ id: cacheItem
+ anchors.fill: verticalBlur
+ visible: root.cached
+ smooth: true
+ sourceItem: verticalBlur
+ hideSource: visible
+ }
+
+}
diff --git a/src/imports/graphicaleffects5/Glow.qml b/src/imports/graphicaleffects5/Glow.qml
index 998e9af..287c6f3 100644
--- a/src/imports/graphicaleffects5/Glow.qml
+++ b/src/imports/graphicaleffects5/Glow.qml
@@ -77,7 +77,16 @@ import Qt5Compat.GraphicalEffects.private
*/
Item {
- id: rootItem
+ id: root
+
+ DropShadowBase {
+ id: dps
+ anchors.fill: parent
+ color: "white"
+ spread: 0.5
+ horizontalOffset: 0
+ verticalOffset: 0
+ }
/*!
This property defines the source item that is going to be used as source
@@ -86,14 +95,27 @@ Item {
\note It is not supported to let the effect include itself, for
instance by setting source to the effect's parent.
*/
- property variant source
+ property alias source: dps.source
/*!
Radius defines the softness of the glow. A larger radius causes the
edges of the glow to appear more blurry.
- The value ranges from 0.0 (no blur) to inf. By default, the property is
- set to \c 0.0 (no blur).
+ Depending on the radius value, value of the \l{Glow::samples}{samples}
+ should be set to sufficiently large to ensure the visual quality.
+
+ The ideal blur is achieved by selecting \c samples and \c radius such
+ that \c {samples = 1 + radius * 2}, such as:
+
+ \table
+ \header \li Radius \li Samples
+ \row \li 0 \e{(no blur)} \li 1
+ \row \li 1 \li 3
+ \row \li 2 \li 5
+ \row \li 3 \li 7
+ \endtable
+
+ By default, the property is set to \c {floor(samples/2)}.
\table
\header
@@ -109,6 +131,10 @@ Item {
\li \b { radius: 6 }
\li \b { radius: 12 }
\row
+ \li \l samples: 25
+ \li \l samples: 25
+ \li \l samples: 25
+ \row
\li \l color: #ffffff
\li \l color: #ffffff
\li \l color: #ffffff
@@ -118,15 +144,42 @@ Item {
\li \l spread: 0
\endtable
*/
- property real radius: 0.0
+ property alias radius: dps.radius
+
+ /*!
+ This property defines how many samples are taken per pixel when edge
+ softening blur calculation is done. Larger value produces better
+ quality, but is slower to render.
+
+ Ideally, this value should be twice as large as the highest required
+ radius value plus one, such as:
+
+ \table
+ \header \li Radius \li Samples
+ \row \li 0 \e{(no blur)} \li 1
+ \row \li 1 \li 3
+ \row \li 2 \li 5
+ \row \li 3 \li 7
+ \endtable
+
+ By default, the property is set to \c 9.
+
+ This property is not intended to be animated. Changing this property will
+ cause the underlying OpenGL shaders to be recompiled.
+ */
+ property alias samples: dps.samples
/*!
- This property defines how large part of the glow color is strenghtened
+ This property defines how large part of the glow color is strengthened
near the source edges.
The values range from 0.0 to 1.0. By default, the property is set to \c
0.5.
+ \note The implementation is optimized for medium and low spread values.
+ Depending on the source, spread values closer to 1.0 may yield visually
+ asymmetrical results.
+
\table
\header
\li Output examples with different spread values
@@ -145,12 +198,16 @@ Item {
\li \l radius: 8
\li \l radius: 8
\row
+ \li \l samples: 17
+ \li \l samples: 17
+ \li \l samples: 17
+ \row
\li \l color: #ffffff
\li \l color: #ffffff
\li \l color: #ffffff
\endtable
*/
- property real spread: 0.0
+ property alias spread: dps.spread
/*!
This property defines the RGBA color value which is used for the glow.
@@ -175,13 +232,27 @@ Item {
\li \l radius: 8
\li \l radius: 8
\row
+ \li \l samples: 17
+ \li \l samples: 17
+ \li \l samples: 17
+ \row
\li \l spread: 0.5
\li \l spread: 0.5
\li \l spread: 0.5
\endtable
*/
- property color color: "white"
+ property alias color: dps.color
+
+ /*!
+ \internal
+
+ Starting Qt 5.6, this property has no effect. It is left here
+ for source compatibility only.
+
+ ### Qt 6: remove
+ */
+ property bool fast: false
/*!
This property allows the effect output pixels to be cached in order to
@@ -197,17 +268,20 @@ Item {
By default, the property is set to \c false.
*/
- property bool cached: false
+ property alias cached: dps.cached
/*!
This property determines whether or not the effect has a transparent
border.
- When set to \c true, the exterior of the item is padded with a 1 pixel
- wide transparent edge, making sampling outside the source texture use
+ When set to \c true, the exterior of the item is padded with a
+ transparent edge, making sampling outside the source texture use
transparency instead of the edge pixels. Without this property, an
image which has opaque edges will not get a blurred edge.
+ By default, the property is set to \c true. Set it to false if the source
+ already has a transparent edge to make the blurring a tiny bit faster.
+
In the snippet below, the Rectangle on the left has transparent borders
and has blurred edges, whereas the Rectangle on the right does not.
@@ -215,33 +289,5 @@ Item {
\image Glow-transparentBorder.png
*/
- property bool transparentBorder: false
-
- Loader {
- anchors.fill: parent
- sourceComponent: fastGlow
- }
-
- Component {
- id: fastGlow
- FastGlow {
- anchors.fill: parent
- source: sourceProxy.output
- blur: Math.pow(rootItem.radius / 64.0, 0.4)
- color: rootItem.color
- cached: rootItem.cached
- spread: rootItem.spread
- transparentBorder: rootItem.transparentBorder
- }
- }
-
- SourceProxy {
- id: sourceProxy
- input: rootItem.source
- sourceRect: rootItem.transparentBorder ? Qt.rect(-1, -1, parent.width + 2.0, parent.height + 2.0) : Qt.rect(0, 0, 0, 0)
- }
- ShaderEffect {
- anchors.fill: parent
- property variant source: sourceProxy.output
- }
+ property alias transparentBorder: dps.transparentBorder
}
diff --git a/src/imports/graphicaleffects5/InnerShadow.qml b/src/imports/graphicaleffects5/InnerShadow.qml
new file mode 100644
index 0000000..15cdee6
--- /dev/null
+++ b/src/imports/graphicaleffects5/InnerShadow.qml
@@ -0,0 +1,386 @@
+/****************************************************************************
+**
+** Copyright (C) 2022 The Qt Company Ltd.
+** Contact: https://www.qt.io/licensing/
+**
+** This file is part of the Qt Graphical Effects module.
+**
+** $QT_BEGIN_LICENSE:LGPL$
+** Commercial License Usage
+** Licensees holding valid commercial Qt licenses may use this file in
+** accordance with the commercial license agreement provided with the
+** Software or, alternatively, in accordance with the terms contained in
+** a written agreement between you and The Qt Company. For licensing terms
+** and conditions see https://www.qt.io/terms-conditions. For further
+** information use the contact form at https://www.qt.io/contact-us.
+**
+** GNU Lesser General Public License Usage
+** Alternatively, this file may be used under the terms of the GNU Lesser
+** General Public License version 3 as published by the Free Software
+** Foundation and appearing in the file LICENSE.LGPL3 included in the
+** packaging of this file. Please review the following information to
+** ensure the GNU Lesser General Public License version 3 requirements
+** will be met: https://www.gnu.org/licenses/lgpl-3.0.html.
+**
+** GNU General Public License Usage
+** Alternatively, this file may be used under the terms of the GNU
+** General Public License version 2.0 or (at your option) the GNU General
+** Public license version 3 or any later version approved by the KDE Free
+** Qt Foundation. The licenses are as published by the Free Software
+** Foundation and appearing in the file LICENSE.GPL2 and LICENSE.GPL3
+** included in the packaging of this file. Please review the following
+** information to ensure the GNU General Public License requirements will
+** be met: https://www.gnu.org/licenses/gpl-2.0.html and
+** https://www.gnu.org/licenses/gpl-3.0.html.
+**
+** $QT_END_LICENSE$
+**
+****************************************************************************/
+
+import QtQuick
+import Qt5Compat.GraphicalEffects.private
+
+/*!
+ \qmltype InnerShadow
+ \inqmlmodule Qt5Compat.GraphicalEffects
+ \since QtGraphicalEffects 1.0
+ \inherits QtQuick2::Item
+ \ingroup qtgraphicaleffects-drop-shadow
+ \brief Generates a colorized and blurred shadow inside the
+ source.
+
+ By default the effect produces a high quality shadow image, thus the
+ rendering speed of the shadow might not be the highest possible. The
+ rendering speed is reduced especially if the shadow edges are heavily
+ softened. For use cases that require faster rendering speed and for which
+ the highest possible visual quality is not necessary, property
+ \l{InnerShadow::fast}{fast} can be set to true.
+
+ \table
+ \header
+ \li Source
+ \li Effect applied
+ \row
+ \li \image Original_butterfly.png
+ \li \image InnerShadow_butterfly.png
+ \endtable
+
+ \note This effect is available when running with OpenGL.
+
+ \section1 Example
+
+ The following example shows how to apply the effect.
+ \snippet InnerShadow-example.qml example
+
+*/
+Item {
+ id: rootItem
+
+ /*!
+ This property defines the source item that is going to be used as the
+ source for the generated shadow.
+
+ \note It is not supported to let the effect include itself, for
+ instance by setting source to the effect's parent.
+ */
+ property variant source
+
+ /*!
+ Radius defines the softness of the shadow. A larger radius causes the
+ edges of the shadow to appear more blurry.
+
+ Depending on the radius value, value of the
+ \l{InnerShadow::samples}{samples} should be set to sufficiently large to
+ ensure the visual quality.
+
+ The value ranges from 0.0 (no blur) to inf. By default, the property is
+ set to \c 0.0 (no blur).
+
+ \table
+ \header
+ \li Output examples with different radius values
+ \li
+ \li
+ \row
+ \li \image InnerShadow_radius1.png
+ \li \image InnerShadow_radius2.png
+ \li \image InnerShadow_radius3.png
+ \row
+ \li \b { radius: 0 }
+ \li \b { radius: 6 }
+ \li \b { radius: 12 }
+ \row
+ \li \l samples: 24
+ \li \l samples: 24
+ \li \l samples: 24
+ \row
+ \li \l color: #000000
+ \li \l color: #000000
+ \li \l color: #000000
+ \row
+ \li \l horizontalOffset: 0
+ \li \l horizontalOffset: 0
+ \li \l horizontalOffset: 0
+ \row
+ \li \l verticalOffset: 0
+ \li \l verticalOffset: 0
+ \li \l verticalOffset: 0
+ \row
+ \li \l spread: 0
+ \li \l spread: 0
+ \li \l spread: 0
+ \endtable
+
+ */
+ property real radius: 0.0
+
+ /*!
+ This property defines how many samples are taken per pixel when edge
+ softening blur calculation is done. Larger value produces better
+ quality, but is slower to render.
+
+ Ideally, this value should be twice as large as the highest required
+ radius value, for example, if the radius is animated between 0.0 and
+ 4.0, samples should be set to 8.
+
+ The value ranges from 0 to 32. By default, the property is set to \c 0.
+
+ This property is not intended to be animated. Changing this property may
+ cause the underlying OpenGL shaders to be recompiled.
+
+ When \l{InnerShadow::fast}{fast} property is set to true, this property
+ has no effect.
+
+ */
+ property int samples: 0
+
+ /*!
+ This property defines how large part of the shadow color is strengthened
+ near the source edges.
+
+ The value ranges from 0.0 to 1.0. By default, the property is set to \c
+ 0.5.
+
+ \table
+ \header
+ \li Output examples with different spread values
+ \li
+ \li
+ \row
+ \li \image InnerShadow_spread1.png
+ \li \image InnerShadow_spread2.png
+ \li \image InnerShadow_spread3.png
+ \row
+ \li \b { spread: 0.0 }
+ \li \b { spread: 0.3 }
+ \li \b { spread: 0.5 }
+ \row
+ \li \l radius: 16
+ \li \l radius: 16
+ \li \l radius: 16
+ \row
+ \li \l samples: 24
+ \li \l samples: 24
+ \li \l samples: 24
+ \row
+ \li \l color: #000000
+ \li \l color: #000000
+ \li \l color: #000000
+ \row
+ \li \l horizontalOffset: 0
+ \li \l horizontalOffset: 0
+ \li \l horizontalOffset: 0
+ \row
+ \li \l verticalOffset: 0
+ \li \l verticalOffset: 0
+ \li \l verticalOffset: 0
+ \endtable
+
+ */
+ property real spread: 0.0
+
+ /*!
+ This property defines the RGBA color value which is used for the shadow.
+
+ By default, the property is set to \c "black".
+
+ \table
+ \header
+ \li Output examples with different color values
+ \li
+ \li
+ \row
+ \li \image InnerShadow_color1.png
+ \li \image InnerShadow_color2.png
+ \li \image InnerShadow_color3.png
+ \row
+ \li \b { color: #000000 }
+ \li \b { color: #ffffff }
+ \li \b { color: #ff0000 }
+ \row
+ \li \l radius: 16
+ \li \l radius: 16
+ \li \l radius: 16
+ \row
+ \li \l samples: 24
+ \li \l samples: 24
+ \li \l samples: 24
+ \row
+ \li \l horizontalOffset: 0
+ \li \l horizontalOffset: 0
+ \li \l horizontalOffset: 0
+ \row
+ \li \l verticalOffset: 0
+ \li \l verticalOffset: 0
+ \li \l verticalOffset: 0
+ \row
+ \li \l spread: 0.2
+ \li \l spread: 0.2
+ \li \l spread: 0.2
+ \endtable
+ */
+ property color color: "black"
+
+ /*!
+ \qmlproperty real QtGraphicalEffects::InnerShadow::horizontalOffset
+ \qmlproperty real QtGraphicalEffects::InnerShadow::verticalOffset
+
+ HorizontalOffset and verticalOffset properties define the offset for the
+ rendered shadow compared to the InnerShadow item position. Often, the
+ InnerShadow item is anchored so that it fills the source element. In
+ this case, if the HorizontalOffset and verticalOffset properties are set
+ to 0, the shadow is rendered fully inside the source item. By changing
+ the offset properties, the shadow can be positioned relatively to the
+ source item.
+
+ The values range from -inf to inf. By default, the properties are set to
+ \c 0.
+
+ \table
+ \header
+ \li Output examples with different horizontalOffset values
+ \li
+ \li
+ \row
+ \li \image InnerShadow_horizontalOffset1.png
+ \li \image InnerShadow_horizontalOffset2.png
+ \li \image InnerShadow_horizontalOffset3.png
+ \row
+ \li \b { horizontalOffset: -20 }
+ \li \b { horizontalOffset: 0 }
+ \li \b { horizontalOffset: 20 }
+ \row
+ \li \l radius: 16
+ \li \l radius: 16
+ \li \l radius: 16
+ \row
+ \li \l samples: 24
+ \li \l samples: 24
+ \li \l samples: 24
+ \row
+ \li \l color: #000000
+ \li \l color: #000000
+ \li \l color: #000000
+ \row
+ \li \l verticalOffset: 0
+ \li \l verticalOffset: 0
+ \li \l verticalOffset: 0
+ \row
+ \li \l spread: 0
+ \li \l spread: 0
+ \li \l spread: 0
+ \endtable
+
+ */
+ property real horizontalOffset: 0
+ property real verticalOffset: 0
+
+ /*!
+ This property selects the blurring algorithm that is used to produce the
+ softness for the effect. Setting this to true enables fast algorithm,
+ setting value to false produces higher quality result.
+
+ By default, the property is set to \c false.
+
+ \table
+ \header
+ \li Output examples with different fast values
+ \li
+ \li
+ \row
+ \li \image InnerShadow_fast1.png
+ \li \image InnerShadow_fast2.png
+ \row
+ \li \b { fast: false }
+ \li \b { fast: true }
+ \row
+ \li \l radius: 16
+ \li \l radius: 16
+ \row
+ \li \l samples: 24
+ \li \l samples: 24
+ \row
+ \li \l color: #000000
+ \li \l color: #000000
+ \row
+ \li \l horizontalOffset: 0
+ \li \l horizontalOffset: 0
+ \row
+ \li \l verticalOffset: 0
+ \li \l verticalOffset: 0
+ \row
+ \li \l spread: 0.2
+ \li \l spread: 0.2
+ \endtable
+ */
+ property bool fast: false
+
+ /*!
+ This property allows the effect output pixels to be cached in order to
+ improve the rendering performance. Every time the source or effect
+ properties are changed, the pixels in the cache must be updated. Memory
+ consumption is increased, because an extra buffer of memory is required
+ for storing the effect output.
+
+ It is recommended to disable the cache when the source or the effect
+ properties are animated.
+
+ By default, the property is set to \c false.
+
+ */
+ property bool cached: false
+
+ Loader {
+ anchors.fill: parent
+ sourceComponent: rootItem.fast ? innerShadow : gaussianInnerShadow
+ }
+
+ Component {
+ id: gaussianInnerShadow
+ GaussianInnerShadow {
+ anchors.fill: parent
+ source: rootItem.source
+ radius: rootItem.radius
+ maximumRadius: rootItem.samples * 0.5
+ color: rootItem.color
+ cached: rootItem.cached
+ spread: rootItem.spread
+ horizontalOffset: rootItem.horizontalOffset
+ verticalOffset: rootItem.verticalOffset
+ }
+ }
+
+ Component {
+ id: innerShadow
+ FastInnerShadow {
+ anchors.fill: parent
+ source: rootItem.source
+ blur: Math.pow(rootItem.radius / 64.0, 0.4)
+ color: rootItem.color
+ cached: rootItem.cached
+ spread: rootItem.spread
+ horizontalOffset: rootItem.horizontalOffset
+ verticalOffset: rootItem.verticalOffset
+ }
+ }
+}
diff --git a/src/imports/graphicaleffects5/MaskedBlur.qml b/src/imports/graphicaleffects5/MaskedBlur.qml
new file mode 100644
index 0000000..145b4d4
--- /dev/null
+++ b/src/imports/graphicaleffects5/MaskedBlur.qml
@@ -0,0 +1,192 @@
+/****************************************************************************
+**
+** Copyright (C) 2022 The Qt Company Ltd.
+** Copyright (C) 2017 Jolla Ltd, author: <gunnar.sletta@jollamobile.com>
+** Contact: https://www.qt.io/licensing/
+**
+** This file is part of the Qt Graphical Effects module.
+**
+** $QT_BEGIN_LICENSE:LGPL$
+** Commercial License Usage
+** Licensees holding valid commercial Qt licenses may use this file in
+** accordance with the commercial license agreement provided with the
+** Software or, alternatively, in accordance with the terms contained in
+** a written agreement between you and The Qt Company. For licensing terms
+** and conditions see https://www.qt.io/terms-conditions. For further
+** information use the contact form at https://www.qt.io/contact-us.
+**
+** GNU Lesser General Public License Usage
+** Alternatively, this file may be used under the terms of the GNU Lesser
+** General Public License version 3 as published by the Free Software
+** Foundation and appearing in the file LICENSE.LGPL3 included in the
+** packaging of this file. Please review the following information to
+** ensure the GNU Lesser General Public License version 3 requirements
+** will be met: https://www.gnu.org/licenses/lgpl-3.0.html.
+**
+** GNU General Public License Usage
+** Alternatively, this file may be used under the terms of the GNU
+** General Public License version 2.0 or (at your option) the GNU General
+** Public license version 3 or any later version approved by the KDE Free
+** Qt Foundation. The licenses are as published by the Free Software
+** Foundation and appearing in the file LICENSE.GPL2 and LICENSE.GPL3
+** included in the packaging of this file. Please review the following
+** information to ensure the GNU General Public License requirements will
+** be met: https://www.gnu.org/licenses/gpl-2.0.html and
+** https://www.gnu.org/licenses/gpl-3.0.html.
+**
+** $QT_END_LICENSE$
+**
+****************************************************************************/
+
+import QtQuick
+import Qt5Compat.GraphicalEffects.private
+
+/*!
+ \qmltype MaskedBlur
+ \inqmlmodule Qt5Compat.GraphicalEffects
+ \since QtGraphicalEffects 1.0
+ \inherits QtQuick2::Item
+ \ingroup qtgraphicaleffects-blur
+ \brief Applies a blur effect with a varying intesity.
+
+ MaskedBlur effect softens the image by blurring it. The intensity of the
+ blur can be controlled for each pixel using maskSource so that some parts of
+ the source are blurred more than others.
+
+ Performing blur live is a costly operation. Fullscreen gaussian blur
+ with even a moderate number of samples will only run at 60 fps on highend
+ graphics hardware.
+
+ \table
+ \header
+ \li Source
+ \li MaskSource
+ \li Effect applied
+ \row
+ \li \image Original_bug.png
+ \li \image MaskedBlur_mask.png
+ \li \image MaskedBlur_bug.png
+ \endtable
+
+ \note This effect is available when running with OpenGL.
+
+ \section1 Example
+
+ The following example shows how to apply the effect.
+ \snippet MaskedBlur-example.qml example
+
+*/
+Item {
+ id: root
+
+ /*!
+ This property defines the source item that is going to be blurred.
+
+ \note It is not supported to let the effect include itself, for
+ instance by setting source to the effect's parent.
+ */
+ property alias source: blur.source
+
+ /*!
+ This property defines the item that is controlling the final intensity
+ of the blur. The pixel alpha channel value from maskSource defines the
+ actual blur radius that is going to be used for blurring the
+ corresponding source pixel.
+
+ Opaque maskSource pixels produce blur with specified
+ \l{MaskedBlur::radius}{radius}, while transparent pixels suppress the
+ blur completely. Semitransparent maskSource pixels produce blur with a
+ radius that is interpolated according to the pixel transparency level.
+ */
+ property alias maskSource: maskProxy.input
+
+ /*!
+ This property defines the distance of the neighboring pixels which
+ affect the blurring of an individual pixel. A larger radius increases
+ the blur effect.
+
+ Depending on the radius value, value of the
+ \l{MaskedBlur::samples}{samples} should be set to sufficiently large to
+ ensure the visual quality.
+
+ The value ranges from 0.0 (no blur) to inf. By default, the property is
+ set to \c 0.0 (no blur).
+
+ \table
+ \header
+ \li Output examples with different radius values
+ \li
+ \li
+ \row
+ \li \image MaskedBlur_radius1.png
+ \li \image MaskedBlur_radius2.png
+ \li \image MaskedBlur_radius3.png
+ \row
+ \li \b { radius: 0 }
+ \li \b { radius: 8 }
+ \li \b { radius: 16 }
+ \row
+ \li \l samples: 25
+ \li \l samples: 25
+ \li \l samples: 25
+ \endtable
+
+ */
+ property alias radius: blur.radius
+
+ /*!
+ This property defines how many samples are taken per pixel when blur
+ calculation is done. Larger value produces better quality, but is slower
+ to render.
+
+ Ideally, this value should be twice as large as the highest required
+ radius value plus 1, for example, if the radius is animated between 0.0
+ and 4.0, samples should be set to 9.
+
+ By default, the property is set to \c 9.
+
+ This property is not intended to be animated. Changing this property may
+ cause the underlying OpenGL shaders to be recompiled.
+ */
+ property alias samples: blur.samples
+
+ /*!
+ This property allows the effect output pixels to be cached in order to
+ improve the rendering performance. Every time the source or effect
+ properties are changed, the pixels in the cache must be updated. Memory
+ consumption is increased, because an extra buffer of memory is required
+ for storing the effect output.
+
+ It is recommended to disable the cache when the source or the effect
+ properties are animated.
+
+ By default, the property is set to \c false.
+
+ */
+ property alias cached: cacheItem.visible
+
+ GaussianBlur {
+ id: blur
+
+ source: root.source;
+ anchors.fill: parent
+ _maskSource: maskProxy.output;
+
+ SourceProxy {
+ id: maskProxy
+ }
+ }
+
+ ShaderEffectSource {
+ id: cacheItem
+ x: -blur._kernelRadius
+ y: -blur._kernelRadius
+ width: blur.width + 2 * blur._kernelRadius
+ height: blur.height + 2 * blur._kernelRadius
+ visible: false
+ smooth: true
+ sourceRect: Qt.rect(-blur._kernelRadius, -blur._kernelRadius, width, height);
+ sourceItem: blur
+ hideSource: visible
+ }
+}
diff --git a/src/imports/graphicaleffects5/RadialBlur.qml b/src/imports/graphicaleffects5/RadialBlur.qml
new file mode 100644
index 0000000..2c4ad01
--- /dev/null
+++ b/src/imports/graphicaleffects5/RadialBlur.qml
@@ -0,0 +1,322 @@
+/****************************************************************************
+**
+** Copyright (C) 2022 The Qt Company Ltd.
+** Contact: https://www.qt.io/licensing/
+**
+** This file is part of the Qt Graphical Effects module.
+**
+** $QT_BEGIN_LICENSE:LGPL$
+** Commercial License Usage
+** Licensees holding valid commercial Qt licenses may use this file in
+** accordance with the commercial license agreement provided with the
+** Software or, alternatively, in accordance with the terms contained in
+** a written agreement between you and The Qt Company. For licensing terms
+** and conditions see https://www.qt.io/terms-conditions. For further
+** information use the contact form at https://www.qt.io/contact-us.
+**
+** GNU Lesser General Public License Usage
+** Alternatively, this file may be used under the terms of the GNU Lesser
+** General Public License version 3 as published by the Free Software
+** Foundation and appearing in the file LICENSE.LGPL3 included in the
+** packaging of this file. Please review the following information to
+** ensure the GNU Lesser General Public License version 3 requirements
+** will be met: https://www.gnu.org/licenses/lgpl-3.0.html.
+**
+** GNU General Public License Usage
+** Alternatively, this file may be used under the terms of the GNU
+** General Public License version 2.0 or (at your option) the GNU General
+** Public license version 3 or any later version approved by the KDE Free
+** Qt Foundation. The licenses are as published by the Free Software
+** Foundation and appearing in the file LICENSE.GPL2 and LICENSE.GPL3
+** included in the packaging of this file. Please review the following
+** information to ensure the GNU General Public License requirements will
+** be met: https://www.gnu.org/licenses/gpl-2.0.html and
+** https://www.gnu.org/licenses/gpl-3.0.html.
+**
+** $QT_END_LICENSE$
+**
+****************************************************************************/
+
+import QtQuick
+import Qt5Compat.GraphicalEffects.private
+
+/*!
+ \qmltype RadialBlur
+ \inqmlmodule Qt5Compat.GraphicalEffects
+ \since Qt5Compat.GraphicalEffects 1.0
+ \inherits QtQuick2::Item
+ \ingroup qtgraphicaleffects-motion-blur
+ \brief Applies directional blur in a circular direction around the items
+ center point.
+
+ Effect creates perceived impression that the source item appears to be
+ rotating to the direction of the blur.
+
+ Other available motionblur effects are
+ \l{Qt5Compat.GraphicalEffects::ZoomBlur}{ZoomBlur} and
+ \l{Qt5Compat.GraphicalEffects::DirectionalBlur}{DirectionalBlur}.
+
+ \table
+ \header
+ \li Source
+ \li Effect applied
+ \row
+ \li \image Original_bug.png
+ \li \image RadialBlur_bug.png
+ \endtable
+
+ \note This effect is available when running with OpenGL.
+
+ \section1 Example Usage
+
+ The following example shows how to apply the effect.
+ \snippet RadialBlur-example.qml example
+*/
+Item {
+ id: rootItem
+
+ /*!
+ This property defines the source item that is going to be blurred.
+
+ \note It is not supported to let the effect include itself, for
+ instance by setting source to the effect's parent.
+ */
+ property variant source
+
+ /*!
+ This property defines the direction for the blur and at the same time
+ the level of blurring. The larger the angle, the more the result becomes
+ blurred. The quality of the blur depends on
+ \l{RadialBlur::samples}{samples} property. If angle value is large, more
+ samples are needed to keep the visual quality at high level.
+
+ Allowed values are between 0.0 and 360.0. By default the property is set
+ to \c 0.0.
+
+ \table
+ \header
+ \li Output examples with different angle values
+ \li
+ \li
+ \row
+ \li \image RadialBlur_angle1.png
+ \li \image RadialBlur_angle2.png
+ \li \image RadialBlur_angle3.png
+ \row
+ \li \b { angle: 0.0 }
+ \li \b { angle: 15.0 }
+ \li \b { angle: 30.0 }
+ \row
+ \li \l samples: 24
+ \li \l samples: 24
+ \li \l samples: 24
+ \row
+ \li \l horizontalOffset: 0
+ \li \l horizontalOffset: 0
+ \li \l horizontalOffset: 0
+ \row
+ \li \l verticalOffset: 0
+ \li \l verticalOffset: 0
+ \li \l verticalOffset: 0
+ \endtable
+ */
+ property real angle: 0.0
+
+ /*!
+ This property defines how many samples are taken per pixel when blur
+ calculation is done. Larger value produces better quality, but is slower
+ to render.
+
+ This property is not intended to be animated. Changing this property may
+ cause the underlying OpenGL shaders to be recompiled.
+
+ Allowed values are between 0 and inf (practical maximum depends on GPU).
+ By default the property is set to \c 0 (no samples).
+
+ */
+ property int samples: 0
+
+ /*!
+ \qmlproperty real QtGraphicalEffects::RadialBlur::horizontalOffset
+ \qmlproperty real QtGraphicalEffects::RadialBlur::verticalOffset
+
+ These properties define the offset in pixels for the perceived center
+ point of the rotation.
+
+ Allowed values are between -inf and inf.
+ By default these properties are set to \c 0.
+
+ \table
+ \header
+ \li Output examples with different horizontalOffset values
+ \li
+ \li
+ \row
+ \li \image RadialBlur_horizontalOffset1.png
+ \li \image RadialBlur_horizontalOffset2.png
+ \li \image RadialBlur_horizontalOffset3.png
+ \row
+ \li \b { horizontalOffset: 75.0 }
+ \li \b { horizontalOffset: 0.0 }
+ \li \b { horizontalOffset: -75.0 }
+ \row
+ \li \l samples: 24
+ \li \l samples: 24
+ \li \l samples: 24
+ \row
+ \li \l angle: 20
+ \li \l angle: 20
+ \li \l angle: 20
+ \row
+ \li \l verticalOffset: 0
+ \li \l verticalOffset: 0
+ \li \l verticalOffset: 0
+ \endtable
+ */
+ property real horizontalOffset: 0.0
+ property real verticalOffset: 0.0
+
+ /*!
+ This property defines the blur behavior near the edges of the item,
+ where the pixel blurring is affected by the pixels outside the source
+ edges.
+
+ If the property is set to \c true, the pixels outside the source are
+ interpreted to be transparent, which is similar to OpenGL
+ clamp-to-border extension. The blur is expanded slightly outside the
+ effect item area.
+
+ If the property is set to \c false, the pixels outside the source are
+ interpreted to contain the same color as the pixels at the edge of the
+ item, which is similar to OpenGL clamp-to-edge behavior. The blur does
+ not expand outside the effect item area.
+
+ By default, the property is set to \c false.
+ */
+ property bool transparentBorder: false
+
+ /*!
+ This property allows the effect output pixels to be cached in order to
+ improve the rendering performance.
+
+ Every time the source or effect properties are changed, the pixels in
+ the cache must be updated. Memory consumption is increased, because an
+ extra buffer of memory is required for storing the effect output.
+
+ It is recommended to disable the cache when the source or the effect
+ properties are animated.
+
+ By default, the property is set to \c false.
+
+ */
+ property bool cached: false
+
+ SourceProxy {
+ id: sourceProxy
+ input: rootItem.source
+ sourceRect: shaderItem.transparentBorder ? Qt.rect(-1, -1, parent.width + 2.0, parent.height + 2.0) : Qt.rect(0, 0, 0, 0)
+ }
+
+ ShaderEffectSource {
+ id: cacheItem
+ anchors.fill: shaderItem
+ visible: rootItem.cached
+ smooth: true
+ sourceItem: shaderItem
+ live: true
+ hideSource: visible
+ }
+
+ ShaderBuilder {
+ id: shaderBuilder
+ }
+
+ ShaderEffect {
+ id: shaderItem
+ property variant source: sourceProxy.output
+ property variant center: Qt.point(0.5 + rootItem.horizontalOffset / parent.width, 0.5 + rootItem.verticalOffset / parent.height)
+ property bool transparentBorder: rootItem.transparentBorder && rootItem.samples > 1
+ property int samples: rootItem.samples
+ property real weight: 1.0 / Math.max(1.0, rootItem.samples)
+ property real angleSin: Math.sin(rootItem.angle/2 * Math.PI/180)
+ property real angleCos: Math.cos(rootItem.angle/2 * Math.PI/180)
+ property real angleSinStep: Math.sin(-rootItem.angle * Math.PI/180 / Math.max(1.0, rootItem.samples - 1))
+ property real angleCosStep: Math.cos(-rootItem.angle * Math.PI/180 / Math.max(1.0, rootItem.samples - 1))
+ property variant expandPixels: transparentBorder ? Qt.size(0.5 * parent.height, 0.5 * parent.width) : Qt.size(0,0)
+ property variant expand: transparentBorder ? Qt.size(expandPixels.width / width, expandPixels.height / height) : Qt.size(0,0)
+ property variant delta: Qt.size(1.0 / rootItem.width, 1.0 / rootItem.height)
+ property real w: parent.width
+ property real h: parent.height
+
+ x: transparentBorder ? -expandPixels.width - 1 : 0
+ y: transparentBorder ? -expandPixels.height - 1 : 0
+ width: transparentBorder ? parent.width + expandPixels.width * 2.0 + 2 : parent.width
+ height: transparentBorder ? parent.height + expandPixels.height * 2.0 + 2 : parent.height
+
+ property string fragmentShaderSkeleton: "#version 440
+ layout(location = 0) in vec2 qt_TexCoord0;
+ layout(location = 0) out vec4 fragColor;
+
+ layout(std140, binding = 0) uniform buf {
+ mat4 qt_Matrix;
+ float qt_Opacity;
+ float angleSin;
+ float angleCos;
+ float angleSinStep;
+ float angleCosStep;
+ float weight;
+ vec2 expand;
+ vec2 center;
+ vec2 delta;
+ float w;
+ float h;
+ };
+ layout(binding = 1) uniform sampler2D source;
+
+ void main() {
+ mat2 m;
+ fragColor = vec4(0.0);
+ vec2 texCoord = qt_TexCoord0;
+
+ PLACEHOLDER_EXPAND_STEPS
+
+ vec2 dir = vec2(texCoord.s * w - w * center.x, texCoord.t * h - h * center.y);
+ m[0] = vec2(angleCos, -angleSin);
+ m[1] = vec2(angleSin, angleCos);
+ dir *= m;
+
+ m[0] = vec2(angleCosStep, -angleSinStep);
+ m[1] = vec2(angleSinStep, angleCosStep);
+
+ PLACEHOLDER_UNROLLED_LOOP
+
+ fragColor *= weight * qt_Opacity;
+ }
+ "
+
+ function buildFragmentShader() {
+ var shader = fragmentShaderSkeleton
+ var expandSteps = ""
+
+ if (transparentBorder) {
+ expandSteps += "texCoord = (texCoord - expand) / (1.0 - 2.0 * expand);"
+ }
+
+ var unrolledLoop = "fragColor += texture(source, texCoord);\n"
+
+ if (rootItem.samples > 1) {
+ unrolledLoop = ""
+ for (var i = 0; i < rootItem.samples; i++)
+ unrolledLoop += "fragColor += texture(source, center + dir * delta); dir *= m;\n"
+ }
+
+ shader = shader.replace("PLACEHOLDER_EXPAND_STEPS", expandSteps)
+ fragmentShader = shaderBuilder.buildFragmentShader(shader.replace("PLACEHOLDER_UNROLLED_LOOP", unrolledLoop))
+ }
+
+ onFragmentShaderChanged: sourceChanged()
+ onSamplesChanged: buildFragmentShader()
+ onTransparentBorderChanged: buildFragmentShader()
+ Component.onCompleted: buildFragmentShader()
+ }
+}
diff --git a/src/imports/graphicaleffects5/RecursiveBlur.qml b/src/imports/graphicaleffects5/RecursiveBlur.qml
new file mode 100644
index 0000000..90573f3
--- /dev/null
+++ b/src/imports/graphicaleffects5/RecursiveBlur.qml
@@ -0,0 +1,329 @@
+/****************************************************************************
+**
+** Copyright (C) 2022 The Qt Company Ltd.
+** Contact: https://www.qt.io/licensing/
+**
+** This file is part of the Qt Graphical Effects module.
+**
+** $QT_BEGIN_LICENSE:LGPL$
+** Commercial License Usage
+** Licensees holding valid commercial Qt licenses may use this file in
+** accordance with the commercial license agreement provided with the
+** Software or, alternatively, in accordance with the terms contained in
+** a written agreement between you and The Qt Company. For licensing terms
+** and conditions see https://www.qt.io/terms-conditions. For further
+** information use the contact form at https://www.qt.io/contact-us.
+**
+** GNU Lesser General Public License Usage
+** Alternatively, this file may be used under the terms of the GNU Lesser
+** General Public License version 3 as published by the Free Software
+** Foundation and appearing in the file LICENSE.LGPL3 included in the
+** packaging of this file. Please review the following information to
+** ensure the GNU Lesser General Public License version 3 requirements
+** will be met: https://www.gnu.org/licenses/lgpl-3.0.html.
+**
+** GNU General Public License Usage
+** Alternatively, this file may be used under the terms of the GNU
+** General Public License version 2.0 or (at your option) the GNU General
+** Public license version 3 or any later version approved by the KDE Free
+** Qt Foundation. The licenses are as published by the Free Software
+** Foundation and appearing in the file LICENSE.GPL2 and LICENSE.GPL3
+** included in the packaging of this file. Please review the following
+** information to ensure the GNU General Public License requirements will
+** be met: https://www.gnu.org/licenses/gpl-2.0.html and
+** https://www.gnu.org/licenses/gpl-3.0.html.
+**
+** $QT_END_LICENSE$
+**
+****************************************************************************/
+
+import QtQuick
+import Qt5Compat.GraphicalEffects.private
+
+/*!
+ \qmltype RecursiveBlur
+ \inqmlmodule Qt5Compat.GraphicalEffects
+ \since QtGraphicalEffects 1.0
+ \inherits QtQuick2::Item
+ \ingroup qtgraphicaleffects-blur
+ \brief Blurs repeatedly, providing a strong blur effect.
+
+ The RecursiveBlur effect softens the image by blurring it with an algorithm
+ that uses a recursive feedback loop to blur the source multiple times. The
+ effect may give more blurry results than
+ \l{Qt5Compat.GraphicalEffects::GaussianBlur}{GaussianBlur} or
+ \l{Qt5Compat.GraphicalEffects::FastBlur}{FastBlur}, but the result is produced
+ asynchronously and takes more time.
+
+ \table
+ \header
+ \li Source
+ \li Effect applied
+ \row
+ \li \image Original_bug.png
+ \li \image RecursiveBlur_bug.png
+ \endtable
+
+ \note This effect is available when running with OpenGL.
+
+ \section1 Example
+
+ The following example shows how to apply the effect.
+ \snippet RecursiveBlur-example.qml example
+
+*/
+Item {
+ id: rootItem
+
+ /*!
+ This property defines the source item that is going to be blurred.
+
+ \note It is not supported to let the effect include itself, for
+ instance by setting source to the effect's parent.
+ */
+ property variant source
+
+ /*!
+ This property defines the distance of neighboring pixels which influence
+ the blurring of individual pixels. A larger radius provides better
+ quality, but is slower to render.
+
+ \b Note: The radius value in this effect is not intended to be changed
+ or animated frequently. The correct way to use it is to set the correct
+ value and keep it unchanged for the whole duration of the iterative blur
+ sequence.
+
+ The value ranges from (no blur) to 16.0 (maximum blur step). By default,
+ the property is set to \c 0.0 (no blur).
+
+ \table
+ \header
+ \li Output examples with different radius values
+ \li
+ \li
+ \row
+ \li \image RecursiveBlur_radius1.png
+ \li \image RecursiveBlur_radius2.png
+ \li \image RecursiveBlur_radius3.png
+ \row
+ \li \b { radius: 2.5 }
+ \li \b { radius: 4.5 }
+ \li \b { radius: 7.5 }
+ \row
+ \li \l loops: 20
+ \li \l loops: 20
+ \li \l loops: 20
+ \endtable
+
+ */
+ property real radius: 0.0
+
+ /*!
+ This property allows the effect output pixels to be cached in order to
+ improve the rendering performance.
+
+ Every time the source or effect properties are changed, the pixels in
+ the cache must be updated. Memory consumption is increased, because an
+ extra buffer of memory is required for storing the effect output.
+
+ It is recommended to disable the cache when the source or the effect
+ properties are animated.
+
+ By default, the property is set to \c false.
+
+ */
+ property bool cached: false
+
+ /*!
+ This property defines the blur behavior near the edges of the item,
+ where the pixel blurring is affected by the pixels outside the source
+ edges.
+
+ If the property is set to \c true, the pixels outside the source are
+ interpreted to be transparent, which is similar to OpenGL
+ clamp-to-border extension. The blur is expanded slightly outside the
+ effect item area.
+
+ If the property is set to \c false, the pixels outside the source are
+ interpreted to contain the same color as the pixels at the edge of the
+ item, which is similar to OpenGL clamp-to-edge behavior. The blur does
+ not expand outside the effect item area.
+
+ By default, the property is set to \c false.
+
+ \table
+ \header
+ \li Output examples with different transparentBorder values
+ \li
+ \li
+ \row
+ \li \image RecursiveBlur_transparentBorder1.png
+ \li \image RecursiveBlur_transparentBorder2.png
+ \row
+ \li \b { transparentBorder: false }
+ \li \b { transparentBorder: true }
+ \row
+ \li \l loops: 20
+ \li \l loops: 20
+ \row
+ \li \l radius: 7.5
+ \li \l radius: 7.5
+ \endtable
+ */
+ property bool transparentBorder: false
+
+ /*!
+ This property defines the amount of blur iterations that are going to be
+ performed for the source. When the property changes, the iterative
+ blurring process starts. If the value is decreased or if the value
+ changes from zero to non-zero, a snapshot is taken from the source. The
+ snapshot is used as a starting point for the process.
+
+ The iteration loop tries to run as fast as possible. The speed might be
+ limited by the VSYNC or the time needed for one blur step, or both.
+ Sometimes it may be desirable to perform the blurring with a slower
+ pace. In that case, it may be convenient to control the property with
+ Animation which increases the value.
+
+ The value ranges from 0 to inf. By default, the property is set to \c 0.
+
+ \table
+ \header
+ \li Output examples with different loops values
+ \li
+ \li
+ \row
+ \li \image RecursiveBlur_loops1.png
+ \li \image RecursiveBlur_loops2.png
+ \li \image RecursiveBlur_loops3.png
+ \row
+ \li \b { loops: 4 }
+ \li \b { loops: 20 }
+ \li \b { loops: 70 }
+ \row
+ \li \l radius: 7.5
+ \li \l radius: 7.5
+ \li \l radius: 7.5
+ \endtable
+
+ */
+ property int loops: 0
+
+ /*!
+ This property holds the progress of asynchronous source blurring
+ process, from 0.0 (nothing blurred) to 1.0 (finished).
+ */
+ property real progress: loops > 0.0 ? Math.min(1.0, recursionTimer.counter / loops) : 0.0
+
+ onLoopsChanged: recursiveSource.scheduleUpdate()
+ onSourceChanged: recursionTimer.reset()
+ onRadiusChanged: recursionTimer.reset()
+ onTransparentBorderChanged: recursionTimer.reset()
+
+ SourceProxy {
+ id: sourceProxy
+ input: rootItem.source
+ sourceRect: rootItem.transparentBorder ? Qt.rect(-1, -1, parent.width + 2, parent.height + 2) : Qt.rect(0, 0, 0, 0)
+ }
+
+ ShaderEffectSource {
+ id: cacheItem
+ anchors.fill: verticalBlur
+ smooth: true
+ visible: rootItem.cached
+ hideSource: visible
+ live: true
+ sourceItem: inputItem.visible ? inputItem : verticalBlur
+ }
+
+ Item {
+ id: recursionTimer
+ property int counter: 0
+
+ function reset() {
+ counter = 0
+ recursiveSource.scheduleUpdate()
+ }
+
+ function nextFrame() {
+ if (loops < counter)
+ recursionTimer.counter = 0
+
+ if (counter > 0)
+ recursiveSource.sourceItem = verticalBlur
+ else
+ recursiveSource.sourceItem = inputItem
+
+ if (counter < loops) {
+ recursiveSource.scheduleUpdate()
+ counter++
+ }
+ }
+ }
+
+ ShaderEffect {
+ id: inputItem
+ property variant source: sourceProxy.output
+ property real expandX: rootItem.transparentBorder ? (horizontalBlur.maximumRadius) / horizontalBlur.width : 0.0
+ property real expandY: rootItem.transparentBorder ? (horizontalBlur.maximumRadius) / horizontalBlur.height : 0.0
+
+ anchors.fill: verticalBlur
+ visible: !verticalBlur.visible
+
+ vertexShader: "qrc:/qt-project.org/imports/Qt5Compat/GraphicalEffects/shaders_ng/recursiveblur.vert.qsb"
+
+ fragmentShader: "qrc:/qt-project.org/imports/Qt5Compat/GraphicalEffects/shaders_ng/recursiveblur.frag.qsb"
+ }
+
+ ShaderEffectSource {
+ id: recursiveSource
+ visible: false
+ smooth: true
+ hideSource: false
+ live: false
+ sourceItem: inputItem
+ recursive: true
+ onSourceItemChanged: scheduleUpdate()
+ onScheduledUpdateCompleted: recursionTimer.nextFrame()
+ }
+
+ GaussianDirectionalBlur {
+ id: verticalBlur
+ x: rootItem.transparentBorder ? -horizontalBlur.maximumRadius - 1 : 0
+ y: rootItem.transparentBorder ? -horizontalBlur.maximumRadius - 1 : 0
+ width: horizontalBlur.width + 2
+ height: horizontalBlur.height + 2
+
+ horizontalStep: 0.0
+ verticalStep: 1.0 / parent.height
+
+ source: ShaderEffectSource {
+ sourceItem: horizontalBlur
+ hideSource: true
+ visible: false
+ smooth: true
+ }
+
+ deviation: (radius + 1) / 2.3333
+ radius: rootItem.radius
+ maximumRadius: Math.ceil(rootItem.radius)
+ transparentBorder: false
+ visible: loops > 0
+ }
+
+ GaussianDirectionalBlur {
+ id: horizontalBlur
+ width: rootItem.transparentBorder ? parent.width + 2 * maximumRadius + 2 : parent.width
+ height: rootItem.transparentBorder ? parent.height + 2 * maximumRadius + 2 : parent.height
+
+ horizontalStep: 1.0 / parent.width
+ verticalStep: 0.0
+
+ source: recursiveSource
+ deviation: (radius + 1) / 2.3333
+ radius: rootItem.radius
+ maximumRadius: Math.ceil(rootItem.radius)
+ transparentBorder: false
+ visible: false
+ }
+}
diff --git a/src/imports/graphicaleffects5/ZoomBlur.qml b/src/imports/graphicaleffects5/ZoomBlur.qml
new file mode 100644
index 0000000..5bd0802
--- /dev/null
+++ b/src/imports/graphicaleffects5/ZoomBlur.qml
@@ -0,0 +1,312 @@
+/****************************************************************************
+**
+** Copyright (C) 2022 The Qt Company Ltd.
+** Contact: https://www.qt.io/licensing/
+**
+** This file is part of the Qt Graphical Effects module.
+**
+** $QT_BEGIN_LICENSE:LGPL$
+** Commercial License Usage
+** Licensees holding valid commercial Qt licenses may use this file in
+** accordance with the commercial license agreement provided with the
+** Software or, alternatively, in accordance with the terms contained in
+** a written agreement between you and The Qt Company. For licensing terms
+** and conditions see https://www.qt.io/terms-conditions. For further
+** information use the contact form at https://www.qt.io/contact-us.
+**
+** GNU Lesser General Public License Usage
+** Alternatively, this file may be used under the terms of the GNU Lesser
+** General Public License version 3 as published by the Free Software
+** Foundation and appearing in the file LICENSE.LGPL3 included in the
+** packaging of this file. Please review the following information to
+** ensure the GNU Lesser General Public License version 3 requirements
+** will be met: https://www.gnu.org/licenses/lgpl-3.0.html.
+**
+** GNU General Public License Usage
+** Alternatively, this file may be used under the terms of the GNU
+** General Public License version 2.0 or (at your option) the GNU General
+** Public license version 3 or any later version approved by the KDE Free
+** Qt Foundation. The licenses are as published by the Free Software
+** Foundation and appearing in the file LICENSE.GPL2 and LICENSE.GPL3
+** included in the packaging of this file. Please review the following
+** information to ensure the GNU General Public License requirements will
+** be met: https://www.gnu.org/licenses/gpl-2.0.html and
+** https://www.gnu.org/licenses/gpl-3.0.html.
+**
+** $QT_END_LICENSE$
+**
+****************************************************************************/
+
+import QtQuick
+import Qt5Compat.GraphicalEffects.private
+
+/*!
+ \qmltype ZoomBlur
+ \inqmlmodule Qt5Compat.GraphicalEffects
+ \since Qt5Compat.GraphicalEffects 1.0
+ \inherits QtQuick2::Item
+ \ingroup qtgraphicaleffects-motion-blur
+ \brief Applies directional blur effect towards source items center point.
+
+ Effect creates perceived impression that the source item appears to be
+ moving towards the center point in Z-direction or that the camera appears
+ to be zooming rapidly. Other available motion blur effects are
+ \l{Qt5Compat.GraphicalEffects::DirectionalBlur}{DirectionalBlur}
+ and \l{Qt5Compat.GraphicalEffects::RadialBlur}{RadialBlur}.
+
+ \table
+ \header
+ \li Source
+ \li Effect applied
+ \row
+ \li \image Original_bug.png
+ \li \image ZoomBlur_bug.png
+ \endtable
+
+ \note This effect is available when running with OpenGL.
+
+ \section1 Example
+
+ The following example shows how to apply the effect.
+ \snippet ZoomBlur-example.qml example
+
+*/
+Item {
+ id: rootItem
+
+ /*!
+ This property defines the source item that is going to be blurred.
+
+ \note It is not supported to let the effect include itself, for
+ instance by setting source to the effect's parent.
+ */
+ property variant source
+
+ /*!
+ This property defines the maximum perceived amount of movement for each
+ pixel. The amount is smaller near the center and reaches the specified
+ value at the edges.
+
+ The quality of the blur depends on \l{ZoomBlur::samples}{samples}
+ property. If length value is large, more samples are needed to keep the
+ visual quality at high level.
+
+ The value ranges from 0.0 to inf. By default the property is set to \c
+ 0.0 (no blur).
+
+ \table
+ \header
+ \li Output examples with different length values
+ \li
+ \li
+ \row
+ \li \image ZoomBlur_length1.png
+ \li \image ZoomBlur_length2.png
+ \li \image ZoomBlur_length3.png
+ \row
+ \li \b { length: 0.0 }
+ \li \b { length: 32.0 }
+ \li \b { length: 48.0 }
+ \row
+ \li \l samples: 24
+ \li \l samples: 24
+ \li \l samples: 24
+ \row
+ \li \l horizontalOffset: 0
+ \li \l horizontalOffset: 0
+ \li \l horizontalOffset: 0
+ \row
+ \li \l verticalOffset: 0
+ \li \l verticalOffset: 0
+ \li \l verticalOffset: 0
+ \endtable
+
+ */
+ property real length: 0.0
+
+ /*!
+ This property defines how many samples are taken per pixel when blur
+ calculation is done. Larger value produces better quality, but is slower
+ to render.
+
+ This property is not intended to be animated. Changing this property may
+ cause the underlying OpenGL shaders to be recompiled.
+
+ Allowed values are between 0 and inf (practical maximum depends on GPU).
+ By default the property is set to \c 0 (no samples).
+
+ */
+ property int samples: 0
+
+ /*!
+ \qmlproperty real QtGraphicalEffects::ZoomBlur::horizontalOffset
+ \qmlproperty real QtGraphicalEffects::ZoomBlur::verticalOffset
+
+ These properties define an offset in pixels for the blur direction
+ center point.
+
+ The values range from -inf to inf. By default these properties are set
+ to \c 0.
+
+ \table
+ \header
+ \li Output examples with different horizontalOffset values
+ \li
+ \li
+ \row
+ \li \image ZoomBlur_horizontalOffset1.png
+ \li \image ZoomBlur_horizontalOffset2.png
+ \li \image ZoomBlur_horizontalOffset3.png
+ \row
+ \li \b { horizontalOffset: 100.0 }
+ \li \b { horizontalOffset: 0.0 }
+ \li \b { horizontalOffset: -100.0 }
+ \row
+ \li \l samples: 24
+ \li \l samples: 24
+ \li \l samples: 24
+ \row
+ \li \l length: 32
+ \li \l length: 32
+ \li \l length: 32
+ \row
+ \li \l verticalOffset: 0
+ \li \l verticalOffset: 0
+ \li \l verticalOffset: 0
+ \endtable
+ */
+ property real horizontalOffset: 0.0
+ property real verticalOffset: 0.0
+
+ /*!
+ This property defines the blur behavior near the edges of the item,
+ where the pixel blurring is affected by the pixels outside the source
+ edges.
+
+ If the property is set to \c true, the pixels outside the source are
+ interpreted to be transparent, which is similar to OpenGL
+ clamp-to-border extension. The blur is expanded slightly outside the
+ effect item area.
+
+ If the property is set to \c false, the pixels outside the source are
+ interpreted to contain the same color as the pixels at the edge of the
+ item, which is similar to OpenGL clamp-to-edge behavior. The blur does
+ not expand outside the effect item area.
+
+ By default, the property is set to \c false.
+
+ */
+ property bool transparentBorder: false
+
+ /*!
+ This property allows the effect output pixels to be cached in order to
+ improve the rendering performance.
+
+ Every time the source or effect properties are changed, the pixels in
+ the cache must be updated. Memory consumption is increased, because an
+ extra buffer of memory is required for storing the effect output.
+
+ It is recommended to disable the cache when the source or the effect
+ properties are animated.
+
+ By default, the property is set to \c false.
+ */
+ property bool cached: false
+
+ SourceProxy {
+ id: sourceProxy
+ input: rootItem.source
+ sourceRect: rootItem.transparentBorder ? Qt.rect(-1, -1, parent.width + 2.0, parent.height + 2.0) : Qt.rect(0, 0, 0, 0)
+ }
+
+ ShaderEffectSource {
+ id: cacheItem
+ anchors.fill: shaderItem
+ visible: rootItem.cached
+ smooth: true
+ sourceItem: shaderItem
+ live: true
+ hideSource: visible
+ }
+
+ ShaderBuilder {
+ id: shaderBuilder
+ }
+
+ ShaderEffect {
+ id: shaderItem
+ property variant source: sourceProxy.output
+ property variant center: Qt.point(0.5 + rootItem.horizontalOffset / width, 0.5 + rootItem.verticalOffset / height)
+ property real len: rootItem.length
+ property bool transparentBorder: rootItem.transparentBorder
+ property real samples: rootItem.samples
+ property real weight: 1.0 / Math.max(1.0, rootItem.samples)
+ property variant expandPixels: transparentBorder ? Qt.size(rootItem.samples, rootItem.samples) : Qt.size(0,0)
+ property variant expand: transparentBorder ? Qt.size(expandPixels.width / width, expandPixels.height / height) : Qt.size(0,0)
+ property variant delta: Qt.size(1.0 / rootItem.width, 1.0 / rootItem.height)
+
+ x: transparentBorder ? -expandPixels.width - 1 : 0
+ y: transparentBorder ? -expandPixels.height - 1 : 0
+ width: transparentBorder ? parent.width + 2.0 * expandPixels.width + 2 : parent.width
+ height: transparentBorder ? parent.height + 2.0 * expandPixels.height + 2 : parent.height
+
+ property string fragmentShaderSkeleton: "#version 440
+ layout(location = 0) in vec2 qt_TexCoord0;
+ layout(location = 0) out vec4 fragColor;
+
+ layout(std140, binding = 0) uniform buf {
+ mat4 qt_Matrix;
+ float qt_Opacity;
+ float len;
+ float weight;
+ float samples;
+ vec2 center;
+ vec2 expand;
+ vec2 delta;
+ };
+ layout(binding = 1) uniform sampler2D source;
+
+ void main() {
+ vec2 texCoord = qt_TexCoord0;
+ vec2 centerCoord = center;
+
+ PLACEHOLDER_EXPAND_STEPS
+
+ vec2 dir = vec2(centerCoord.x - texCoord.s, centerCoord.y - texCoord.t);
+ dir /= max(1.0, length(dir) * 2.0);
+ vec2 shift = delta * len * dir * 2.0 / max(1.0, samples - 1.0);
+ fragColor = vec4(0.0);
+
+ PLACEHOLDER_UNROLLED_LOOP
+
+ fragColor *= weight * qt_Opacity;
+ }
+ "
+
+ function buildFragmentShader() {
+ var shader = fragmentShaderSkeleton
+ var expandSteps = ""
+
+ if (transparentBorder) {
+ expandSteps += "centerCoord = (centerCoord - expand) / (1.0 - 2.0 * expand);"
+ expandSteps += "texCoord = (texCoord - expand) / (1.0 - 2.0 * expand);"
+ }
+
+ var unrolledLoop = "fragColor += texture(source, texCoord);\n"
+
+ if (rootItem.samples > 1) {
+ unrolledLoop = ""
+ for (var i = 0; i < rootItem.samples; i++)
+ unrolledLoop += "fragColor += texture(source, texCoord); texCoord += shift;\n"
+ }
+
+ shader = shader.replace("PLACEHOLDER_EXPAND_STEPS", expandSteps)
+ fragmentShader = shaderBuilder.buildFragmentShader(shader.replace("PLACEHOLDER_UNROLLED_LOOP", unrolledLoop))
+ }
+
+ onFragmentShaderChanged: sourceChanged()
+ onSamplesChanged: buildFragmentShader()
+ onTransparentBorderChanged: buildFragmentShader()
+ Component.onCompleted: buildFragmentShader()
+ }
+}
diff --git a/src/imports/graphicaleffects5/doc/images/Blend_bug_and_butterfly.png b/src/imports/graphicaleffects5/doc/images/Blend_bug_and_butterfly.png
new file mode 100644
index 0000000..e7c6f79
--- /dev/null
+++ b/src/imports/graphicaleffects5/doc/images/Blend_bug_and_butterfly.png
Binary files differ
diff --git a/src/imports/graphicaleffects5/doc/images/Blend_mode1.png b/src/imports/graphicaleffects5/doc/images/Blend_mode1.png
new file mode 100644
index 0000000..4ac773d
--- /dev/null
+++ b/src/imports/graphicaleffects5/doc/images/Blend_mode1.png
Binary files differ
diff --git a/src/imports/graphicaleffects5/doc/images/Blend_mode10.png b/src/imports/graphicaleffects5/doc/images/Blend_mode10.png
new file mode 100644
index 0000000..282725b
--- /dev/null
+++ b/src/imports/graphicaleffects5/doc/images/Blend_mode10.png
Binary files differ
diff --git a/src/imports/graphicaleffects5/doc/images/Blend_mode11.png b/src/imports/graphicaleffects5/doc/images/Blend_mode11.png
new file mode 100644
index 0000000..e4e0db6
--- /dev/null
+++ b/src/imports/graphicaleffects5/doc/images/Blend_mode11.png
Binary files differ
diff --git a/src/imports/graphicaleffects5/doc/images/Blend_mode12.png b/src/imports/graphicaleffects5/doc/images/Blend_mode12.png
new file mode 100644
index 0000000..0f9c98a
--- /dev/null
+++ b/src/imports/graphicaleffects5/doc/images/Blend_mode12.png
Binary files differ
diff --git a/src/imports/graphicaleffects5/doc/images/Blend_mode13.png b/src/imports/graphicaleffects5/doc/images/Blend_mode13.png
new file mode 100644
index 0000000..ac2567c
--- /dev/null
+++ b/src/imports/graphicaleffects5/doc/images/Blend_mode13.png
Binary files differ
diff --git a/src/imports/graphicaleffects5/doc/images/Blend_mode14.png b/src/imports/graphicaleffects5/doc/images/Blend_mode14.png
new file mode 100644
index 0000000..cea329b
--- /dev/null
+++ b/src/imports/graphicaleffects5/doc/images/Blend_mode14.png
Binary files differ
diff --git a/src/imports/graphicaleffects5/doc/images/Blend_mode15.png b/src/imports/graphicaleffects5/doc/images/Blend_mode15.png
new file mode 100644
index 0000000..5c7bc40
--- /dev/null
+++ b/src/imports/graphicaleffects5/doc/images/Blend_mode15.png
Binary files differ
diff --git a/src/imports/graphicaleffects5/doc/images/Blend_mode16.png b/src/imports/graphicaleffects5/doc/images/Blend_mode16.png
new file mode 100644
index 0000000..cda82c1
--- /dev/null
+++ b/src/imports/graphicaleffects5/doc/images/Blend_mode16.png
Binary files differ
diff --git a/src/imports/graphicaleffects5/doc/images/Blend_mode17.png b/src/imports/graphicaleffects5/doc/images/Blend_mode17.png
new file mode 100644
index 0000000..7dfa8d8
--- /dev/null
+++ b/src/imports/graphicaleffects5/doc/images/Blend_mode17.png
Binary files differ
diff --git a/src/imports/graphicaleffects5/doc/images/Blend_mode18.png b/src/imports/graphicaleffects5/doc/images/Blend_mode18.png
new file mode 100644
index 0000000..25cd7b0
--- /dev/null
+++ b/src/imports/graphicaleffects5/doc/images/Blend_mode18.png
Binary files differ
diff --git a/src/imports/graphicaleffects5/doc/images/Blend_mode19.png b/src/imports/graphicaleffects5/doc/images/Blend_mode19.png
new file mode 100644
index 0000000..f9565cc
--- /dev/null
+++ b/src/imports/graphicaleffects5/doc/images/Blend_mode19.png
Binary files differ
diff --git a/src/imports/graphicaleffects5/doc/images/Blend_mode2.png b/src/imports/graphicaleffects5/doc/images/Blend_mode2.png
new file mode 100644
index 0000000..0cd57eb
--- /dev/null
+++ b/src/imports/graphicaleffects5/doc/images/Blend_mode2.png
Binary files differ
diff --git a/src/imports/graphicaleffects5/doc/images/Blend_mode20.png b/src/imports/graphicaleffects5/doc/images/Blend_mode20.png
new file mode 100644
index 0000000..80cb192
--- /dev/null
+++ b/src/imports/graphicaleffects5/doc/images/Blend_mode20.png
Binary files differ
diff --git a/src/imports/graphicaleffects5/doc/images/Blend_mode21.png b/src/imports/graphicaleffects5/doc/images/Blend_mode21.png
new file mode 100644
index 0000000..be97d63
--- /dev/null
+++ b/src/imports/graphicaleffects5/doc/images/Blend_mode21.png
Binary files differ
diff --git a/src/imports/graphicaleffects5/doc/images/Blend_mode22.png b/src/imports/graphicaleffects5/doc/images/Blend_mode22.png
new file mode 100644
index 0000000..a5d0280
--- /dev/null
+++ b/src/imports/graphicaleffects5/doc/images/Blend_mode22.png
Binary files differ
diff --git a/src/imports/graphicaleffects5/doc/images/Blend_mode3.png b/src/imports/graphicaleffects5/doc/images/Blend_mode3.png
new file mode 100644
index 0000000..cd14337
--- /dev/null
+++ b/src/imports/graphicaleffects5/doc/images/Blend_mode3.png
Binary files differ
diff --git a/src/imports/graphicaleffects5/doc/images/Blend_mode4.png b/src/imports/graphicaleffects5/doc/images/Blend_mode4.png
new file mode 100644
index 0000000..509b372
--- /dev/null
+++ b/src/imports/graphicaleffects5/doc/images/Blend_mode4.png
Binary files differ
diff --git a/src/imports/graphicaleffects5/doc/images/Blend_mode5.png b/src/imports/graphicaleffects5/doc/images/Blend_mode5.png
new file mode 100644
index 0000000..8f557c0
--- /dev/null
+++ b/src/imports/graphicaleffects5/doc/images/Blend_mode5.png
Binary files differ
diff --git a/src/imports/graphicaleffects5/doc/images/Blend_mode6.png b/src/imports/graphicaleffects5/doc/images/Blend_mode6.png
new file mode 100644
index 0000000..de85ea6
--- /dev/null
+++ b/src/imports/graphicaleffects5/doc/images/Blend_mode6.png
Binary files differ
diff --git a/src/imports/graphicaleffects5/doc/images/Blend_mode7.png b/src/imports/graphicaleffects5/doc/images/Blend_mode7.png
new file mode 100644
index 0000000..11b0b55
--- /dev/null
+++ b/src/imports/graphicaleffects5/doc/images/Blend_mode7.png
Binary files differ
diff --git a/src/imports/graphicaleffects5/doc/images/Blend_mode8.png b/src/imports/graphicaleffects5/doc/images/Blend_mode8.png
new file mode 100644
index 0000000..7376f44
--- /dev/null
+++ b/src/imports/graphicaleffects5/doc/images/Blend_mode8.png
Binary files differ
diff --git a/src/imports/graphicaleffects5/doc/images/Blend_mode9.png b/src/imports/graphicaleffects5/doc/images/Blend_mode9.png
new file mode 100644
index 0000000..ed1aba9
--- /dev/null
+++ b/src/imports/graphicaleffects5/doc/images/Blend_mode9.png
Binary files differ
diff --git a/src/imports/graphicaleffects5/doc/images/DirectionalBlur_angle1.png b/src/imports/graphicaleffects5/doc/images/DirectionalBlur_angle1.png
new file mode 100644
index 0000000..9700f73
--- /dev/null
+++ b/src/imports/graphicaleffects5/doc/images/DirectionalBlur_angle1.png
Binary files differ
diff --git a/src/imports/graphicaleffects5/doc/images/DirectionalBlur_angle2.png b/src/imports/graphicaleffects5/doc/images/DirectionalBlur_angle2.png
new file mode 100644
index 0000000..adf9791
--- /dev/null
+++ b/src/imports/graphicaleffects5/doc/images/DirectionalBlur_angle2.png
Binary files differ
diff --git a/src/imports/graphicaleffects5/doc/images/DirectionalBlur_angle3.png b/src/imports/graphicaleffects5/doc/images/DirectionalBlur_angle3.png
new file mode 100644
index 0000000..7bf2a62
--- /dev/null
+++ b/src/imports/graphicaleffects5/doc/images/DirectionalBlur_angle3.png
Binary files differ
diff --git a/src/imports/graphicaleffects5/doc/images/DirectionalBlur_bug.png b/src/imports/graphicaleffects5/doc/images/DirectionalBlur_bug.png
new file mode 100644
index 0000000..ad2fff5
--- /dev/null
+++ b/src/imports/graphicaleffects5/doc/images/DirectionalBlur_bug.png
Binary files differ
diff --git a/src/imports/graphicaleffects5/doc/images/DirectionalBlur_length1.png b/src/imports/graphicaleffects5/doc/images/DirectionalBlur_length1.png
new file mode 100644
index 0000000..f514ee4
--- /dev/null
+++ b/src/imports/graphicaleffects5/doc/images/DirectionalBlur_length1.png
Binary files differ
diff --git a/src/imports/graphicaleffects5/doc/images/DirectionalBlur_length2.png b/src/imports/graphicaleffects5/doc/images/DirectionalBlur_length2.png
new file mode 100644
index 0000000..9700f73
--- /dev/null
+++ b/src/imports/graphicaleffects5/doc/images/DirectionalBlur_length2.png
Binary files differ
diff --git a/src/imports/graphicaleffects5/doc/images/DirectionalBlur_length3.png b/src/imports/graphicaleffects5/doc/images/DirectionalBlur_length3.png
new file mode 100644
index 0000000..1b3c52c
--- /dev/null
+++ b/src/imports/graphicaleffects5/doc/images/DirectionalBlur_length3.png
Binary files differ
diff --git a/src/imports/graphicaleffects5/doc/images/GaussianBlur_bug.png b/src/imports/graphicaleffects5/doc/images/GaussianBlur_bug.png
new file mode 100644
index 0000000..a9db381
--- /dev/null
+++ b/src/imports/graphicaleffects5/doc/images/GaussianBlur_bug.png
Binary files differ
diff --git a/src/imports/graphicaleffects5/doc/images/GaussianBlur_deviation1.png b/src/imports/graphicaleffects5/doc/images/GaussianBlur_deviation1.png
new file mode 100644
index 0000000..5dcb775
--- /dev/null
+++ b/src/imports/graphicaleffects5/doc/images/GaussianBlur_deviation1.png
Binary files differ
diff --git a/src/imports/graphicaleffects5/doc/images/GaussianBlur_deviation2.png b/src/imports/graphicaleffects5/doc/images/GaussianBlur_deviation2.png
new file mode 100644
index 0000000..68ff492
--- /dev/null
+++ b/src/imports/graphicaleffects5/doc/images/GaussianBlur_deviation2.png
Binary files differ
diff --git a/src/imports/graphicaleffects5/doc/images/GaussianBlur_deviation3.png b/src/imports/graphicaleffects5/doc/images/GaussianBlur_deviation3.png
new file mode 100644
index 0000000..4823e31
--- /dev/null
+++ b/src/imports/graphicaleffects5/doc/images/GaussianBlur_deviation3.png
Binary files differ
diff --git a/src/imports/graphicaleffects5/doc/images/GaussianBlur_deviation4.png b/src/imports/graphicaleffects5/doc/images/GaussianBlur_deviation4.png
new file mode 100644
index 0000000..ba82f8f
--- /dev/null
+++ b/src/imports/graphicaleffects5/doc/images/GaussianBlur_deviation4.png
Binary files differ
diff --git a/src/imports/graphicaleffects5/doc/images/GaussianBlur_deviation_graph.png b/src/imports/graphicaleffects5/doc/images/GaussianBlur_deviation_graph.png
new file mode 100644
index 0000000..2c22008
--- /dev/null
+++ b/src/imports/graphicaleffects5/doc/images/GaussianBlur_deviation_graph.png
Binary files differ
diff --git a/src/imports/graphicaleffects5/doc/images/GaussianBlur_radius1.png b/src/imports/graphicaleffects5/doc/images/GaussianBlur_radius1.png
new file mode 100644
index 0000000..ce02060
--- /dev/null
+++ b/src/imports/graphicaleffects5/doc/images/GaussianBlur_radius1.png
Binary files differ
diff --git a/src/imports/graphicaleffects5/doc/images/GaussianBlur_radius2.png b/src/imports/graphicaleffects5/doc/images/GaussianBlur_radius2.png
new file mode 100644
index 0000000..3ddd227
--- /dev/null
+++ b/src/imports/graphicaleffects5/doc/images/GaussianBlur_radius2.png
Binary files differ
diff --git a/src/imports/graphicaleffects5/doc/images/GaussianBlur_radius3.png b/src/imports/graphicaleffects5/doc/images/GaussianBlur_radius3.png
new file mode 100644
index 0000000..df8f675
--- /dev/null
+++ b/src/imports/graphicaleffects5/doc/images/GaussianBlur_radius3.png
Binary files differ
diff --git a/src/imports/graphicaleffects5/doc/images/GaussianBlur_transparentBorder1.png b/src/imports/graphicaleffects5/doc/images/GaussianBlur_transparentBorder1.png
new file mode 100644
index 0000000..7365ccd
--- /dev/null
+++ b/src/imports/graphicaleffects5/doc/images/GaussianBlur_transparentBorder1.png
Binary files differ
diff --git a/src/imports/graphicaleffects5/doc/images/GaussianBlur_transparentBorder2.png b/src/imports/graphicaleffects5/doc/images/GaussianBlur_transparentBorder2.png
new file mode 100644
index 0000000..e33661c
--- /dev/null
+++ b/src/imports/graphicaleffects5/doc/images/GaussianBlur_transparentBorder2.png
Binary files differ
diff --git a/src/imports/graphicaleffects5/doc/images/InnerShadow_butterfly.png b/src/imports/graphicaleffects5/doc/images/InnerShadow_butterfly.png
new file mode 100644
index 0000000..654929c
--- /dev/null
+++ b/src/imports/graphicaleffects5/doc/images/InnerShadow_butterfly.png
Binary files differ
diff --git a/src/imports/graphicaleffects5/doc/images/InnerShadow_color1.png b/src/imports/graphicaleffects5/doc/images/InnerShadow_color1.png
new file mode 100644
index 0000000..2626e3e
--- /dev/null
+++ b/src/imports/graphicaleffects5/doc/images/InnerShadow_color1.png
Binary files differ
diff --git a/src/imports/graphicaleffects5/doc/images/InnerShadow_color2.png b/src/imports/graphicaleffects5/doc/images/InnerShadow_color2.png
new file mode 100644
index 0000000..807941e
--- /dev/null
+++ b/src/imports/graphicaleffects5/doc/images/InnerShadow_color2.png
Binary files differ
diff --git a/src/imports/graphicaleffects5/doc/images/InnerShadow_color3.png b/src/imports/graphicaleffects5/doc/images/InnerShadow_color3.png
new file mode 100644
index 0000000..43c6365
--- /dev/null
+++ b/src/imports/graphicaleffects5/doc/images/InnerShadow_color3.png
Binary files differ
diff --git a/src/imports/graphicaleffects5/doc/images/InnerShadow_fast1.png b/src/imports/graphicaleffects5/doc/images/InnerShadow_fast1.png
new file mode 100644
index 0000000..bf3e750
--- /dev/null
+++ b/src/imports/graphicaleffects5/doc/images/InnerShadow_fast1.png
Binary files differ
diff --git a/src/imports/graphicaleffects5/doc/images/InnerShadow_fast2.png b/src/imports/graphicaleffects5/doc/images/InnerShadow_fast2.png
new file mode 100644
index 0000000..7a1b5c7
--- /dev/null
+++ b/src/imports/graphicaleffects5/doc/images/InnerShadow_fast2.png
Binary files differ
diff --git a/src/imports/graphicaleffects5/doc/images/InnerShadow_horizontalOffset1.png b/src/imports/graphicaleffects5/doc/images/InnerShadow_horizontalOffset1.png
new file mode 100644
index 0000000..62fd5e2
--- /dev/null
+++ b/src/imports/graphicaleffects5/doc/images/InnerShadow_horizontalOffset1.png
Binary files differ
diff --git a/src/imports/graphicaleffects5/doc/images/InnerShadow_horizontalOffset2.png b/src/imports/graphicaleffects5/doc/images/InnerShadow_horizontalOffset2.png
new file mode 100644
index 0000000..b268697
--- /dev/null
+++ b/src/imports/graphicaleffects5/doc/images/InnerShadow_horizontalOffset2.png
Binary files differ
diff --git a/src/imports/graphicaleffects5/doc/images/InnerShadow_horizontalOffset3.png b/src/imports/graphicaleffects5/doc/images/InnerShadow_horizontalOffset3.png
new file mode 100644
index 0000000..afb2892
--- /dev/null
+++ b/src/imports/graphicaleffects5/doc/images/InnerShadow_horizontalOffset3.png
Binary files differ
diff --git a/src/imports/graphicaleffects5/doc/images/InnerShadow_radius1.png b/src/imports/graphicaleffects5/doc/images/InnerShadow_radius1.png
new file mode 100644
index 0000000..1dd0f39
--- /dev/null
+++ b/src/imports/graphicaleffects5/doc/images/InnerShadow_radius1.png
Binary files differ
diff --git a/src/imports/graphicaleffects5/doc/images/InnerShadow_radius2.png b/src/imports/graphicaleffects5/doc/images/InnerShadow_radius2.png
new file mode 100644
index 0000000..01a0141
--- /dev/null
+++ b/src/imports/graphicaleffects5/doc/images/InnerShadow_radius2.png
Binary files differ
diff --git a/src/imports/graphicaleffects5/doc/images/InnerShadow_radius3.png b/src/imports/graphicaleffects5/doc/images/InnerShadow_radius3.png
new file mode 100644
index 0000000..1bcd6f5
--- /dev/null
+++ b/src/imports/graphicaleffects5/doc/images/InnerShadow_radius3.png
Binary files differ
diff --git a/src/imports/graphicaleffects5/doc/images/InnerShadow_spread1.png b/src/imports/graphicaleffects5/doc/images/InnerShadow_spread1.png
new file mode 100644
index 0000000..b268697
--- /dev/null
+++ b/src/imports/graphicaleffects5/doc/images/InnerShadow_spread1.png
Binary files differ
diff --git a/src/imports/graphicaleffects5/doc/images/InnerShadow_spread2.png b/src/imports/graphicaleffects5/doc/images/InnerShadow_spread2.png
new file mode 100644
index 0000000..8485191
--- /dev/null
+++ b/src/imports/graphicaleffects5/doc/images/InnerShadow_spread2.png
Binary files differ
diff --git a/src/imports/graphicaleffects5/doc/images/InnerShadow_spread3.png b/src/imports/graphicaleffects5/doc/images/InnerShadow_spread3.png
new file mode 100644
index 0000000..563226a
--- /dev/null
+++ b/src/imports/graphicaleffects5/doc/images/InnerShadow_spread3.png
Binary files differ
diff --git a/src/imports/graphicaleffects5/doc/images/MaskedBlur_bug.png b/src/imports/graphicaleffects5/doc/images/MaskedBlur_bug.png
new file mode 100644
index 0000000..c736d8b
--- /dev/null
+++ b/src/imports/graphicaleffects5/doc/images/MaskedBlur_bug.png
Binary files differ
diff --git a/src/imports/graphicaleffects5/doc/images/MaskedBlur_fast1.png b/src/imports/graphicaleffects5/doc/images/MaskedBlur_fast1.png
new file mode 100644
index 0000000..95ca1be
--- /dev/null
+++ b/src/imports/graphicaleffects5/doc/images/MaskedBlur_fast1.png
Binary files differ
diff --git a/src/imports/graphicaleffects5/doc/images/MaskedBlur_fast2.png b/src/imports/graphicaleffects5/doc/images/MaskedBlur_fast2.png
new file mode 100644
index 0000000..8928e25
--- /dev/null
+++ b/src/imports/graphicaleffects5/doc/images/MaskedBlur_fast2.png
Binary files differ
diff --git a/src/imports/graphicaleffects5/doc/images/MaskedBlur_mask.png b/src/imports/graphicaleffects5/doc/images/MaskedBlur_mask.png
new file mode 100644
index 0000000..871c1f9
--- /dev/null
+++ b/src/imports/graphicaleffects5/doc/images/MaskedBlur_mask.png
Binary files differ
diff --git a/src/imports/graphicaleffects5/doc/images/MaskedBlur_radius1.png b/src/imports/graphicaleffects5/doc/images/MaskedBlur_radius1.png
new file mode 100644
index 0000000..c7f85e1
--- /dev/null
+++ b/src/imports/graphicaleffects5/doc/images/MaskedBlur_radius1.png
Binary files differ
diff --git a/src/imports/graphicaleffects5/doc/images/MaskedBlur_radius2.png b/src/imports/graphicaleffects5/doc/images/MaskedBlur_radius2.png
new file mode 100644
index 0000000..51b9651
--- /dev/null
+++ b/src/imports/graphicaleffects5/doc/images/MaskedBlur_radius2.png
Binary files differ
diff --git a/src/imports/graphicaleffects5/doc/images/MaskedBlur_radius3.png b/src/imports/graphicaleffects5/doc/images/MaskedBlur_radius3.png
new file mode 100644
index 0000000..95ca1be
--- /dev/null
+++ b/src/imports/graphicaleffects5/doc/images/MaskedBlur_radius3.png
Binary files differ
diff --git a/src/imports/graphicaleffects5/doc/images/RadialBlur_angle1.png b/src/imports/graphicaleffects5/doc/images/RadialBlur_angle1.png
new file mode 100644
index 0000000..f514ee4
--- /dev/null
+++ b/src/imports/graphicaleffects5/doc/images/RadialBlur_angle1.png
Binary files differ
diff --git a/src/imports/graphicaleffects5/doc/images/RadialBlur_angle2.png b/src/imports/graphicaleffects5/doc/images/RadialBlur_angle2.png
new file mode 100644
index 0000000..20e51f4
--- /dev/null
+++ b/src/imports/graphicaleffects5/doc/images/RadialBlur_angle2.png
Binary files differ
diff --git a/src/imports/graphicaleffects5/doc/images/RadialBlur_angle3.png b/src/imports/graphicaleffects5/doc/images/RadialBlur_angle3.png
new file mode 100644
index 0000000..d1c0270
--- /dev/null
+++ b/src/imports/graphicaleffects5/doc/images/RadialBlur_angle3.png
Binary files differ
diff --git a/src/imports/graphicaleffects5/doc/images/RadialBlur_bug.png b/src/imports/graphicaleffects5/doc/images/RadialBlur_bug.png
new file mode 100644
index 0000000..cf49512
--- /dev/null
+++ b/src/imports/graphicaleffects5/doc/images/RadialBlur_bug.png
Binary files differ
diff --git a/src/imports/graphicaleffects5/doc/images/RadialBlur_horizontalOffset1.png b/src/imports/graphicaleffects5/doc/images/RadialBlur_horizontalOffset1.png
new file mode 100644
index 0000000..dc8afa7
--- /dev/null
+++ b/src/imports/graphicaleffects5/doc/images/RadialBlur_horizontalOffset1.png
Binary files differ
diff --git a/src/imports/graphicaleffects5/doc/images/RadialBlur_horizontalOffset2.png b/src/imports/graphicaleffects5/doc/images/RadialBlur_horizontalOffset2.png
new file mode 100644
index 0000000..272950f
--- /dev/null
+++ b/src/imports/graphicaleffects5/doc/images/RadialBlur_horizontalOffset2.png
Binary files differ
diff --git a/src/imports/graphicaleffects5/doc/images/RadialBlur_horizontalOffset3.png b/src/imports/graphicaleffects5/doc/images/RadialBlur_horizontalOffset3.png
new file mode 100644
index 0000000..a06a454
--- /dev/null
+++ b/src/imports/graphicaleffects5/doc/images/RadialBlur_horizontalOffset3.png
Binary files differ
diff --git a/src/imports/graphicaleffects5/doc/images/RecursiveBlur_bug.png b/src/imports/graphicaleffects5/doc/images/RecursiveBlur_bug.png
new file mode 100644
index 0000000..470eebb
--- /dev/null
+++ b/src/imports/graphicaleffects5/doc/images/RecursiveBlur_bug.png
Binary files differ
diff --git a/src/imports/graphicaleffects5/doc/images/RecursiveBlur_loops1.png b/src/imports/graphicaleffects5/doc/images/RecursiveBlur_loops1.png
new file mode 100644
index 0000000..b9ea62e
--- /dev/null
+++ b/src/imports/graphicaleffects5/doc/images/RecursiveBlur_loops1.png
Binary files differ
diff --git a/src/imports/graphicaleffects5/doc/images/RecursiveBlur_loops2.png b/src/imports/graphicaleffects5/doc/images/RecursiveBlur_loops2.png
new file mode 100644
index 0000000..d710f35
--- /dev/null
+++ b/src/imports/graphicaleffects5/doc/images/RecursiveBlur_loops2.png
Binary files differ
diff --git a/src/imports/graphicaleffects5/doc/images/RecursiveBlur_loops3.png b/src/imports/graphicaleffects5/doc/images/RecursiveBlur_loops3.png
new file mode 100644
index 0000000..e1c18e7
--- /dev/null
+++ b/src/imports/graphicaleffects5/doc/images/RecursiveBlur_loops3.png
Binary files differ
diff --git a/src/imports/graphicaleffects5/doc/images/RecursiveBlur_radius1.png b/src/imports/graphicaleffects5/doc/images/RecursiveBlur_radius1.png
new file mode 100644
index 0000000..2bf1280
--- /dev/null
+++ b/src/imports/graphicaleffects5/doc/images/RecursiveBlur_radius1.png
Binary files differ
diff --git a/src/imports/graphicaleffects5/doc/images/RecursiveBlur_radius2.png b/src/imports/graphicaleffects5/doc/images/RecursiveBlur_radius2.png
new file mode 100644
index 0000000..696f118
--- /dev/null
+++ b/src/imports/graphicaleffects5/doc/images/RecursiveBlur_radius2.png
Binary files differ
diff --git a/src/imports/graphicaleffects5/doc/images/RecursiveBlur_radius3.png b/src/imports/graphicaleffects5/doc/images/RecursiveBlur_radius3.png
new file mode 100644
index 0000000..3710011
--- /dev/null
+++ b/src/imports/graphicaleffects5/doc/images/RecursiveBlur_radius3.png
Binary files differ
diff --git a/src/imports/graphicaleffects5/doc/images/RecursiveBlur_transparentBorder1.png b/src/imports/graphicaleffects5/doc/images/RecursiveBlur_transparentBorder1.png
new file mode 100644
index 0000000..3710011
--- /dev/null
+++ b/src/imports/graphicaleffects5/doc/images/RecursiveBlur_transparentBorder1.png
Binary files differ
diff --git a/src/imports/graphicaleffects5/doc/images/RecursiveBlur_transparentBorder2.png b/src/imports/graphicaleffects5/doc/images/RecursiveBlur_transparentBorder2.png
new file mode 100644
index 0000000..6adbc44
--- /dev/null
+++ b/src/imports/graphicaleffects5/doc/images/RecursiveBlur_transparentBorder2.png
Binary files differ
diff --git a/src/imports/graphicaleffects5/doc/images/ZoomBlur_bug.png b/src/imports/graphicaleffects5/doc/images/ZoomBlur_bug.png
new file mode 100644
index 0000000..5951ac6
--- /dev/null
+++ b/src/imports/graphicaleffects5/doc/images/ZoomBlur_bug.png
Binary files differ
diff --git a/src/imports/graphicaleffects5/doc/images/ZoomBlur_horizontalOffset1.png b/src/imports/graphicaleffects5/doc/images/ZoomBlur_horizontalOffset1.png
new file mode 100644
index 0000000..299fc45
--- /dev/null
+++ b/src/imports/graphicaleffects5/doc/images/ZoomBlur_horizontalOffset1.png
Binary files differ
diff --git a/src/imports/graphicaleffects5/doc/images/ZoomBlur_horizontalOffset2.png b/src/imports/graphicaleffects5/doc/images/ZoomBlur_horizontalOffset2.png
new file mode 100644
index 0000000..190e50b
--- /dev/null
+++ b/src/imports/graphicaleffects5/doc/images/ZoomBlur_horizontalOffset2.png
Binary files differ
diff --git a/src/imports/graphicaleffects5/doc/images/ZoomBlur_horizontalOffset3.png b/src/imports/graphicaleffects5/doc/images/ZoomBlur_horizontalOffset3.png
new file mode 100644
index 0000000..98e0276
--- /dev/null
+++ b/src/imports/graphicaleffects5/doc/images/ZoomBlur_horizontalOffset3.png
Binary files differ
diff --git a/src/imports/graphicaleffects5/doc/images/ZoomBlur_length1.png b/src/imports/graphicaleffects5/doc/images/ZoomBlur_length1.png
new file mode 100644
index 0000000..f514ee4
--- /dev/null
+++ b/src/imports/graphicaleffects5/doc/images/ZoomBlur_length1.png
Binary files differ
diff --git a/src/imports/graphicaleffects5/doc/images/ZoomBlur_length2.png b/src/imports/graphicaleffects5/doc/images/ZoomBlur_length2.png
new file mode 100644
index 0000000..190e50b
--- /dev/null
+++ b/src/imports/graphicaleffects5/doc/images/ZoomBlur_length2.png
Binary files differ
diff --git a/src/imports/graphicaleffects5/doc/images/ZoomBlur_length3.png b/src/imports/graphicaleffects5/doc/images/ZoomBlur_length3.png
new file mode 100644
index 0000000..b6f2817
--- /dev/null
+++ b/src/imports/graphicaleffects5/doc/images/ZoomBlur_length3.png
Binary files differ
diff --git a/src/imports/graphicaleffects5/doc/snippets/Blend-example.qml b/src/imports/graphicaleffects5/doc/snippets/Blend-example.qml
new file mode 100644
index 0000000..de419b0
--- /dev/null
+++ b/src/imports/graphicaleffects5/doc/snippets/Blend-example.qml
@@ -0,0 +1,74 @@
+/****************************************************************************
+**
+** Copyright (C) 2022 The Qt Company Ltd.
+** Contact: https://www.qt.io/licensing/
+**
+** This file is part of the Qt Graphical Effects module.
+**
+** $QT_BEGIN_LICENSE:LGPL$
+** Commercial License Usage
+** Licensees holding valid commercial Qt licenses may use this file in
+** accordance with the commercial license agreement provided with the
+** Software or, alternatively, in accordance with the terms contained in
+** a written agreement between you and The Qt Company. For licensing terms
+** and conditions see https://www.qt.io/terms-conditions. For further
+** information use the contact form at https://www.qt.io/contact-us.
+**
+** GNU Lesser General Public License Usage
+** Alternatively, this file may be used under the terms of the GNU Lesser
+** General Public License version 3 as published by the Free Software
+** Foundation and appearing in the file LICENSE.LGPL3 included in the
+** packaging of this file. Please review the following information to
+** ensure the GNU Lesser General Public License version 3 requirements
+** will be met: https://www.gnu.org/licenses/lgpl-3.0.html.
+**
+** GNU General Public License Usage
+** Alternatively, this file may be used under the terms of the GNU
+** General Public License version 2.0 or (at your option) the GNU General
+** Public license version 3 or any later version approved by the KDE Free
+** Qt Foundation. The licenses are as published by the Free Software
+** Foundation and appearing in the file LICENSE.GPL2 and LICENSE.GPL3
+** included in the packaging of this file. Please review the following
+** information to ensure the GNU General Public License requirements will
+** be met: https://www.gnu.org/licenses/gpl-2.0.html and
+** https://www.gnu.org/licenses/gpl-3.0.html.
+**
+** $QT_END_LICENSE$
+**
+****************************************************************************/
+
+//! [example]
+import QtQuick
+//! [import]
+import Qt5Compat.GraphicalEffects
+//! [import]
+
+Item {
+ width: 300
+ height: 300
+
+ Image {
+ id: bug
+ source: "images/bug.jpg"
+ sourceSize: Qt.size(parent.width, parent.height)
+ smooth: true
+ visible: false
+ }
+
+ Image {
+ id: butterfly
+ source: "images/butterfly.png"
+ sourceSize: Qt.size(parent.width, parent.height)
+ smooth: true
+ visible: false
+ }
+
+ Blend {
+ anchors.fill: bug
+ source: bug
+ foregroundSource: butterfly
+ mode: "subtract"
+ }
+}
+//! [example]
+
diff --git a/src/imports/graphicaleffects5/doc/snippets/DirectionalBlur-example.qml b/src/imports/graphicaleffects5/doc/snippets/DirectionalBlur-example.qml
new file mode 100644
index 0000000..2df223e
--- /dev/null
+++ b/src/imports/graphicaleffects5/doc/snippets/DirectionalBlur-example.qml
@@ -0,0 +1,64 @@
+/****************************************************************************
+**
+** Copyright (C) 2022 The Qt Company Ltd.
+** Contact: https://www.qt.io/licensing/
+**
+** This file is part of the Qt Graphical Effects module.
+**
+** $QT_BEGIN_LICENSE:LGPL$
+** Commercial License Usage
+** Licensees holding valid commercial Qt licenses may use this file in
+** accordance with the commercial license agreement provided with the
+** Software or, alternatively, in accordance with the terms contained in
+** a written agreement between you and The Qt Company. For licensing terms
+** and conditions see https://www.qt.io/terms-conditions. For further
+** information use the contact form at https://www.qt.io/contact-us.
+**
+** GNU Lesser General Public License Usage
+** Alternatively, this file may be used under the terms of the GNU Lesser
+** General Public License version 3 as published by the Free Software
+** Foundation and appearing in the file LICENSE.LGPL3 included in the
+** packaging of this file. Please review the following information to
+** ensure the GNU Lesser General Public License version 3 requirements
+** will be met: https://www.gnu.org/licenses/lgpl-3.0.html.
+**
+** GNU General Public License Usage
+** Alternatively, this file may be used under the terms of the GNU
+** General Public License version 2.0 or (at your option) the GNU General
+** Public license version 3 or any later version approved by the KDE Free
+** Qt Foundation. The licenses are as published by the Free Software
+** Foundation and appearing in the file LICENSE.GPL2 and LICENSE.GPL3
+** included in the packaging of this file. Please review the following
+** information to ensure the GNU General Public License requirements will
+** be met: https://www.gnu.org/licenses/gpl-2.0.html and
+** https://www.gnu.org/licenses/gpl-3.0.html.
+**
+** $QT_END_LICENSE$
+**
+****************************************************************************/
+
+//! [example]
+import QtQuick
+import Qt5Compat.GraphicalEffects
+
+Item {
+ width: 300
+ height: 300
+
+ Image {
+ id: bug
+ source: "images/bug.jpg"
+ sourceSize: Qt.size(parent.width, parent.height)
+ smooth: true
+ visible: false
+ }
+
+ DirectionalBlur {
+ anchors.fill: bug
+ source: bug
+ angle: 90
+ length: 32
+ samples: 24
+ }
+}
+//! [example]
diff --git a/src/imports/graphicaleffects5/doc/snippets/GaussianBlur-example.qml b/src/imports/graphicaleffects5/doc/snippets/GaussianBlur-example.qml
new file mode 100644
index 0000000..cfd313e
--- /dev/null
+++ b/src/imports/graphicaleffects5/doc/snippets/GaussianBlur-example.qml
@@ -0,0 +1,63 @@
+/****************************************************************************
+**
+** Copyright (C) 2022 The Qt Company Ltd.
+** Contact: https://www.qt.io/licensing/
+**
+** This file is part of the Qt Graphical Effects module.
+**
+** $QT_BEGIN_LICENSE:LGPL$
+** Commercial License Usage
+** Licensees holding valid commercial Qt licenses may use this file in
+** accordance with the commercial license agreement provided with the
+** Software or, alternatively, in accordance with the terms contained in
+** a written agreement between you and The Qt Company. For licensing terms
+** and conditions see https://www.qt.io/terms-conditions. For further
+** information use the contact form at https://www.qt.io/contact-us.
+**
+** GNU Lesser General Public License Usage
+** Alternatively, this file may be used under the terms of the GNU Lesser
+** General Public License version 3 as published by the Free Software
+** Foundation and appearing in the file LICENSE.LGPL3 included in the
+** packaging of this file. Please review the following information to
+** ensure the GNU Lesser General Public License version 3 requirements
+** will be met: https://www.gnu.org/licenses/lgpl-3.0.html.
+**
+** GNU General Public License Usage
+** Alternatively, this file may be used under the terms of the GNU
+** General Public License version 2.0 or (at your option) the GNU General
+** Public license version 3 or any later version approved by the KDE Free
+** Qt Foundation. The licenses are as published by the Free Software
+** Foundation and appearing in the file LICENSE.GPL2 and LICENSE.GPL3
+** included in the packaging of this file. Please review the following
+** information to ensure the GNU General Public License requirements will
+** be met: https://www.gnu.org/licenses/gpl-2.0.html and
+** https://www.gnu.org/licenses/gpl-3.0.html.
+**
+** $QT_END_LICENSE$
+**
+****************************************************************************/
+
+//! [example]
+import QtQuick 2.12
+import QtGraphicalEffects 1.12
+
+Item {
+ width: 300
+ height: 300
+
+ Image {
+ id: bug
+ source: "images/bug.jpg"
+ sourceSize: Qt.size(parent.width, parent.height)
+ smooth: true
+ visible: false
+ }
+
+ GaussianBlur {
+ anchors.fill: bug
+ source: bug
+ radius: 8
+ samples: 16
+ }
+}
+//! [example]
diff --git a/src/imports/graphicaleffects5/doc/snippets/InnerShadow-example.qml b/src/imports/graphicaleffects5/doc/snippets/InnerShadow-example.qml
new file mode 100644
index 0000000..f91cf6f
--- /dev/null
+++ b/src/imports/graphicaleffects5/doc/snippets/InnerShadow-example.qml
@@ -0,0 +1,70 @@
+/****************************************************************************
+**
+** Copyright (C) 2022 The Qt Company Ltd.
+** Contact: https://www.qt.io/licensing/
+**
+** This file is part of the Qt Graphical Effects module.
+**
+** $QT_BEGIN_LICENSE:LGPL$
+** Commercial License Usage
+** Licensees holding valid commercial Qt licenses may use this file in
+** accordance with the commercial license agreement provided with the
+** Software or, alternatively, in accordance with the terms contained in
+** a written agreement between you and The Qt Company. For licensing terms
+** and conditions see https://www.qt.io/terms-conditions. For further
+** information use the contact form at https://www.qt.io/contact-us.
+**
+** GNU Lesser General Public License Usage
+** Alternatively, this file may be used under the terms of the GNU Lesser
+** General Public License version 3 as published by the Free Software
+** Foundation and appearing in the file LICENSE.LGPL3 included in the
+** packaging of this file. Please review the following information to
+** ensure the GNU Lesser General Public License version 3 requirements
+** will be met: https://www.gnu.org/licenses/lgpl-3.0.html.
+**
+** GNU General Public License Usage
+** Alternatively, this file may be used under the terms of the GNU
+** General Public License version 2.0 or (at your option) the GNU General
+** Public license version 3 or any later version approved by the KDE Free
+** Qt Foundation. The licenses are as published by the Free Software
+** Foundation and appearing in the file LICENSE.GPL2 and LICENSE.GPL3
+** included in the packaging of this file. Please review the following
+** information to ensure the GNU General Public License requirements will
+** be met: https://www.gnu.org/licenses/gpl-2.0.html and
+** https://www.gnu.org/licenses/gpl-3.0.html.
+**
+** $QT_END_LICENSE$
+**
+****************************************************************************/
+
+//! [example]
+import QtQuick
+import Qt5Compat.GraphicalEffects
+
+Item {
+ width: 300
+ height: 300
+
+ Rectangle {
+ anchors.fill: parent
+ }
+
+ Image {
+ id: butterfly
+ source: "images/butterfly.png"
+ sourceSize: Qt.size(parent.width, parent.height)
+ smooth: true
+ visible: false
+ }
+
+ InnerShadow {
+ anchors.fill: butterfly
+ radius: 8.0
+ samples: 16
+ horizontalOffset: -3
+ verticalOffset: 3
+ color: "#b0000000"
+ source: butterfly
+ }
+}
+//! [example]
diff --git a/src/imports/graphicaleffects5/doc/snippets/MaskedBlur-example.qml b/src/imports/graphicaleffects5/doc/snippets/MaskedBlur-example.qml
new file mode 100644
index 0000000..f435da8
--- /dev/null
+++ b/src/imports/graphicaleffects5/doc/snippets/MaskedBlur-example.qml
@@ -0,0 +1,76 @@
+/****************************************************************************
+**
+** Copyright (C) 2022 The Qt Company Ltd.
+** Contact: https://www.qt.io/licensing/
+**
+** This file is part of the Qt Graphical Effects module.
+**
+** $QT_BEGIN_LICENSE:LGPL$
+** Commercial License Usage
+** Licensees holding valid commercial Qt licenses may use this file in
+** accordance with the commercial license agreement provided with the
+** Software or, alternatively, in accordance with the terms contained in
+** a written agreement between you and The Qt Company. For licensing terms
+** and conditions see https://www.qt.io/terms-conditions. For further
+** information use the contact form at https://www.qt.io/contact-us.
+**
+** GNU Lesser General Public License Usage
+** Alternatively, this file may be used under the terms of the GNU Lesser
+** General Public License version 3 as published by the Free Software
+** Foundation and appearing in the file LICENSE.LGPL3 included in the
+** packaging of this file. Please review the following information to
+** ensure the GNU Lesser General Public License version 3 requirements
+** will be met: https://www.gnu.org/licenses/lgpl-3.0.html.
+**
+** GNU General Public License Usage
+** Alternatively, this file may be used under the terms of the GNU
+** General Public License version 2.0 or (at your option) the GNU General
+** Public license version 3 or any later version approved by the KDE Free
+** Qt Foundation. The licenses are as published by the Free Software
+** Foundation and appearing in the file LICENSE.GPL2 and LICENSE.GPL3
+** included in the packaging of this file. Please review the following
+** information to ensure the GNU General Public License requirements will
+** be met: https://www.gnu.org/licenses/gpl-2.0.html and
+** https://www.gnu.org/licenses/gpl-3.0.html.
+**
+** $QT_END_LICENSE$
+**
+****************************************************************************/
+
+//! [example]
+import QtQuick
+import Qt5Compat.GraphicalEffects
+
+Item {
+ width: 300
+ height: 300
+
+ Image {
+ id: bug
+ source: "images/bug.jpg"
+ sourceSize: Qt.size(parent.width, parent.height)
+ smooth: true
+ visible: false
+ }
+
+ LinearGradient {
+ id: mask
+ anchors.fill: bug
+ gradient: Gradient {
+ GradientStop { position: 0.2; color: "#ffffffff" }
+ GradientStop { position: 0.5; color: "#00ffffff" }
+ }
+ start: Qt.point(0, 0)
+ end: Qt.point(300, 0)
+ visible: false
+ }
+
+ MaskedBlur {
+ anchors.fill: bug
+ source: bug
+ maskSource: mask
+ radius: 16
+ samples: 24
+ }
+}
+//! [example]
diff --git a/src/imports/graphicaleffects5/doc/snippets/RadialBlur-example.qml b/src/imports/graphicaleffects5/doc/snippets/RadialBlur-example.qml
new file mode 100644
index 0000000..c3ae6f1
--- /dev/null
+++ b/src/imports/graphicaleffects5/doc/snippets/RadialBlur-example.qml
@@ -0,0 +1,63 @@
+/****************************************************************************
+**
+** Copyright (C) 2022 The Qt Company Ltd.
+** Contact: https://www.qt.io/licensing/
+**
+** This file is part of the Qt Graphical Effects module.
+**
+** $QT_BEGIN_LICENSE:LGPL$
+** Commercial License Usage
+** Licensees holding valid commercial Qt licenses may use this file in
+** accordance with the commercial license agreement provided with the
+** Software or, alternatively, in accordance with the terms contained in
+** a written agreement between you and The Qt Company. For licensing terms
+** and conditions see https://www.qt.io/terms-conditions. For further
+** information use the contact form at https://www.qt.io/contact-us.
+**
+** GNU Lesser General Public License Usage
+** Alternatively, this file may be used under the terms of the GNU Lesser
+** General Public License version 3 as published by the Free Software
+** Foundation and appearing in the file LICENSE.LGPL3 included in the
+** packaging of this file. Please review the following information to
+** ensure the GNU Lesser General Public License version 3 requirements
+** will be met: https://www.gnu.org/licenses/lgpl-3.0.html.
+**
+** GNU General Public License Usage
+** Alternatively, this file may be used under the terms of the GNU
+** General Public License version 2.0 or (at your option) the GNU General
+** Public license version 3 or any later version approved by the KDE Free
+** Qt Foundation. The licenses are as published by the Free Software
+** Foundation and appearing in the file LICENSE.GPL2 and LICENSE.GPL3
+** included in the packaging of this file. Please review the following
+** information to ensure the GNU General Public License requirements will
+** be met: https://www.gnu.org/licenses/gpl-2.0.html and
+** https://www.gnu.org/licenses/gpl-3.0.html.
+**
+** $QT_END_LICENSE$
+**
+****************************************************************************/
+
+//! [example]
+import QtQuick
+import Qt5Compat.GraphicalEffects
+
+Item {
+ width: 300
+ height: 300
+
+ Image {
+ id: bug
+ source: "images/bug.jpg"
+ sourceSize: Qt.size(parent.width, parent.height)
+ smooth: true
+ visible: false
+ }
+
+ RadialBlur {
+ anchors.fill: bug
+ source: bug
+ samples: 24
+ angle: 30
+ }
+}
+//! [example]
diff --git a/src/imports/graphicaleffects5/doc/snippets/RecursiveBlur-example.qml b/src/imports/graphicaleffects5/doc/snippets/RecursiveBlur-example.qml
new file mode 100644
index 0000000..f866642
--- /dev/null
+++ b/src/imports/graphicaleffects5/doc/snippets/RecursiveBlur-example.qml
@@ -0,0 +1,63 @@
+/****************************************************************************
+**
+** Copyright (C) 2022 The Qt Company Ltd.
+** Contact: https://www.qt.io/licensing/
+**
+** This file is part of the Qt Graphical Effects module.
+**
+** $QT_BEGIN_LICENSE:LGPL$
+** Commercial License Usage
+** Licensees holding valid commercial Qt licenses may use this file in
+** accordance with the commercial license agreement provided with the
+** Software or, alternatively, in accordance with the terms contained in
+** a written agreement between you and The Qt Company. For licensing terms
+** and conditions see https://www.qt.io/terms-conditions. For further
+** information use the contact form at https://www.qt.io/contact-us.
+**
+** GNU Lesser General Public License Usage
+** Alternatively, this file may be used under the terms of the GNU Lesser
+** General Public License version 3 as published by the Free Software
+** Foundation and appearing in the file LICENSE.LGPL3 included in the
+** packaging of this file. Please review the following information to
+** ensure the GNU Lesser General Public License version 3 requirements
+** will be met: https://www.gnu.org/licenses/lgpl-3.0.html.
+**
+** GNU General Public License Usage
+** Alternatively, this file may be used under the terms of the GNU
+** General Public License version 2.0 or (at your option) the GNU General
+** Public license version 3 or any later version approved by the KDE Free
+** Qt Foundation. The licenses are as published by the Free Software
+** Foundation and appearing in the file LICENSE.GPL2 and LICENSE.GPL3
+** included in the packaging of this file. Please review the following
+** information to ensure the GNU General Public License requirements will
+** be met: https://www.gnu.org/licenses/gpl-2.0.html and
+** https://www.gnu.org/licenses/gpl-3.0.html.
+**
+** $QT_END_LICENSE$
+**
+****************************************************************************/
+
+//! [example]
+import QtQuick
+import Qt5Compat.GraphicalEffects
+
+Item {
+ width: 300
+ height: 300
+
+ Image {
+ id: bug
+ source: "images/bug.jpg"
+ sourceSize: Qt.size(parent.width, parent.height)
+ smooth: true
+ visible: false
+ }
+
+ RecursiveBlur {
+ anchors.fill: bug
+ source: bug
+ radius: 7.5
+ loops: 50
+ }
+}
+//! [example]
diff --git a/src/imports/graphicaleffects5/doc/snippets/ZoomBlur-example.qml b/src/imports/graphicaleffects5/doc/snippets/ZoomBlur-example.qml
new file mode 100644
index 0000000..7199efe
--- /dev/null
+++ b/src/imports/graphicaleffects5/doc/snippets/ZoomBlur-example.qml
@@ -0,0 +1,63 @@
+/****************************************************************************
+**
+** Copyright (C) 2022 The Qt Company Ltd.
+** Contact: https://www.qt.io/licensing/
+**
+** This file is part of the Qt Graphical Effects module.
+**
+** $QT_BEGIN_LICENSE:LGPL$
+** Commercial License Usage
+** Licensees holding valid commercial Qt licenses may use this file in
+** accordance with the commercial license agreement provided with the
+** Software or, alternatively, in accordance with the terms contained in
+** a written agreement between you and The Qt Company. For licensing terms
+** and conditions see https://www.qt.io/terms-conditions. For further
+** information use the contact form at https://www.qt.io/contact-us.
+**
+** GNU Lesser General Public License Usage
+** Alternatively, this file may be used under the terms of the GNU Lesser
+** General Public License version 3 as published by the Free Software
+** Foundation and appearing in the file LICENSE.LGPL3 included in the
+** packaging of this file. Please review the following information to
+** ensure the GNU Lesser General Public License version 3 requirements
+** will be met: https://www.gnu.org/licenses/lgpl-3.0.html.
+**
+** GNU General Public License Usage
+** Alternatively, this file may be used under the terms of the GNU
+** General Public License version 2.0 or (at your option) the GNU General
+** Public license version 3 or any later version approved by the KDE Free
+** Qt Foundation. The licenses are as published by the Free Software
+** Foundation and appearing in the file LICENSE.GPL2 and LICENSE.GPL3
+** included in the packaging of this file. Please review the following
+** information to ensure the GNU General Public License requirements will
+** be met: https://www.gnu.org/licenses/gpl-2.0.html and
+** https://www.gnu.org/licenses/gpl-3.0.html.
+**
+** $QT_END_LICENSE$
+**
+****************************************************************************/
+
+//! [example]
+import QtQuick
+import Qt5Compat.GraphicalEffects
+
+Item {
+ width: 300
+ height: 300
+
+ Image {
+ id: butterfly
+ source: "images/bug.jpg"
+ sourceSize: Qt.size(parent.width, parent.height)
+ smooth: true
+ visible: false
+ }
+
+ ZoomBlur {
+ anchors.fill: butterfly
+ source: butterfly
+ samples: 24
+ length: 48
+ }
+}
+//! [example]
diff --git a/src/imports/graphicaleffects5/doc/src/overview-graphicaleffects5.qdoc b/src/imports/graphicaleffects5/doc/src/overview-graphicaleffects5.qdoc
index 203c154..cf80b86 100644
--- a/src/imports/graphicaleffects5/doc/src/overview-graphicaleffects5.qdoc
+++ b/src/imports/graphicaleffects5/doc/src/overview-graphicaleffects5.qdoc
@@ -31,19 +31,7 @@
\brief Effects provided by the Qt Graphical Effects API
The Qt Graphical Effects module is provided for compatibility with
- applications written for Qt 5. As far as practically feasible, effects
- have been ported, but some dynamically generated effects are incompatible with
- the approach to shader effects in Qt 6 and have thus been left out:
-
- \list
- \li Blend
- \li InnerShadow
- \li All blur effects besides FastBlur: GaussianBlur, MaskedBlur, RecursiveBlur,
- DirectionalBlur, RadialBlur, ZoomBlur.
- \endlist
-
- Dependencies on any of these types have to be replaced by a custom shader effect
- in the application code.
+ applications written for Qt 5.
Effects are visual items that can be added to Qt Quick user interface as UI
components. To import the Qt Graphical Effects types, include the Qt
@@ -61,6 +49,9 @@
The following list presents the functional division of types that are part
of Qt Graphical Effects:
+ \section1 Blend
+ \annotatedlist qtgraphicaleffects-blend
+
\section1 Color
\annotatedlist qtgraphicaleffects-color
@@ -76,6 +67,9 @@
\section1 Blur
\annotatedlist qtgraphicaleffects-blur
+ \section1 Motion Blur
+ \annotatedlist qtgraphicaleffects-motion-blur
+
\section1 Glow
\annotatedlist qtgraphicaleffects-glow
diff --git a/src/imports/graphicaleffects5/doc/src/qtgraphicaleffects5.qdoc b/src/imports/graphicaleffects5/doc/src/qtgraphicaleffects5.qdoc
index 4f0a111..7f6e109 100644
--- a/src/imports/graphicaleffects5/doc/src/qtgraphicaleffects5.qdoc
+++ b/src/imports/graphicaleffects5/doc/src/qtgraphicaleffects5.qdoc
@@ -53,15 +53,13 @@
\brief Qt Graphical Effects module is a Qt Quick Add-On module.
The Qt Graphical Effects module is provided for compatibility with
-applications written for Qt 5. As far as practically feasible, effects
-have been ported, but some dynamically generated effects are incompatible with
-the approach to shader effects in Qt 6 and have thus been left out.
+applications written for Qt 5.
The Qt Graphical Effects module provides a set of QML types for adding visually
impressive and configurable effects to user interfaces. Effects are visual
items that can be added to Qt Quick user interface as UI components.
-The API consists of over 15 effects provided as separate QML types. The effects
+The API consists of over 20 effects provided as separate QML types. The effects
cover functional areas such as masking, blurring, coloring, and many more.
\section1 Getting Started
@@ -81,10 +79,13 @@ Properties can be animated just like any other QML properties. The QML type
documentation contains property descriptions and basic usage examples.
\note Effects are not available when running with the \c software
-backend of Qt Quick. For more information on Qt Quick scene graph
+backend of Qt Quick. For more information on Qt Quick scene graph
backends, see \l{qtquick-visualcanvas-adaptations.html}{Scene Graph
Adaptations}.
+\note Runtime-generated effects such as GaussianBlur will store the shader-files in temporary
+storage using QTemporaryFile, thus they require a writable file system.
+
\section1 QML Types
\generatelist {qmltypesbymodule Qt5Compat.GraphicalEffects}
\noautolist
diff --git a/src/imports/graphicaleffects5/private/CMakeLists.txt b/src/imports/graphicaleffects5/private/CMakeLists.txt
index 4b4e850..4852bf6 100644
--- a/src/imports/graphicaleffects5/private/CMakeLists.txt
+++ b/src/imports/graphicaleffects5/private/CMakeLists.txt
@@ -3,7 +3,13 @@
#####################################################################
set(qml_files
+ "DropShadowBase.qml"
"FastGlow.qml"
+ "FastInnerShadow.qml"
+ "GaussianDirectionalBlur.qml"
+ "GaussianGlow.qml"
+ "GaussianInnerShadow.qml"
+ "GaussianMaskedBlur.qml"
)
qt_internal_add_qml_module(qtgraphicaleffectsprivate
@@ -18,6 +24,7 @@ qt_internal_add_qml_module(qtgraphicaleffectsprivate
SOURCES
plugin.cpp
qgfxsourceproxy.cpp qgfxsourceproxy_p.h
+ qgfxshaderbuilder.cpp qgfxshaderbuilder_p.h
QML_FILES
${qml_files}
LIBRARIES
@@ -25,4 +32,6 @@ qt_internal_add_qml_module(qtgraphicaleffectsprivate
Qt::GuiPrivate
Qt::QmlPrivate
Qt::QuickPrivate
+ Qt::ShaderTools
+ Qt::ShaderToolsPrivate
)
diff --git a/src/imports/graphicaleffects5/private/DropShadowBase.qml b/src/imports/graphicaleffects5/private/DropShadowBase.qml
new file mode 100644
index 0000000..5577647
--- /dev/null
+++ b/src/imports/graphicaleffects5/private/DropShadowBase.qml
@@ -0,0 +1,98 @@
+/****************************************************************************
+**
+** Copyright (C) 2017 Jolla Ltd, author: <gunnar.sletta@jollamobile.com>
+** Contact: http://www.qt-project.org/legal
+**
+** This file is part of the Qt Graphical Effects module.
+**
+** $QT_BEGIN_LICENSE:LGPL$
+** Commercial License Usage
+** Licensees holding valid commercial Qt licenses may use this file in
+** accordance with the commercial license agreement provided with the
+** Software or, alternatively, in accordance with the terms contained in
+** a written agreement between you and The Qt Company. For licensing terms
+** and conditions see https://www.qt.io/terms-conditions. For further
+** information use the contact form at https://www.qt.io/contact-us.
+**
+** GNU Lesser General Public License Usage
+** Alternatively, this file may be used under the terms of the GNU Lesser
+** General Public License version 3 as published by the Free Software
+** Foundation and appearing in the file LICENSE.LGPL3 included in the
+** packaging of this file. Please review the following information to
+** ensure the GNU Lesser General Public License version 3 requirements
+** will be met: https://www.gnu.org/licenses/lgpl-3.0.html.
+**
+** GNU General Public License Usage
+** Alternatively, this file may be used under the terms of the GNU
+** General Public License version 2.0 or (at your option) the GNU General
+** Public license version 3 or any later version approved by the KDE Free
+** Qt Foundation. The licenses are as published by the Free Software
+** Foundation and appearing in the file LICENSE.GPL2 and LICENSE.GPL3
+** included in the packaging of this file. Please review the following
+** information to ensure the GNU General Public License requirements will
+** be met: https://www.gnu.org/licenses/gpl-2.0.html and
+** https://www.gnu.org/licenses/gpl-3.0.html.
+**
+** $QT_END_LICENSE$
+**
+****************************************************************************/
+
+import QtQuick
+import Qt5Compat.GraphicalEffects.private
+import Qt5Compat.GraphicalEffects
+
+Item {
+ id: root
+
+ property variant source
+ property real radius: Math.floor(samples / 2)
+ property int samples: 9
+ property color color: "black"
+ property real horizontalOffset: 0
+ property real verticalOffset: 0
+ property real spread: 0.0
+ property bool cached: false
+ property bool transparentBorder: true
+
+ GaussianBlur {
+ id: blur
+ width: parent.width
+ height: parent.height
+ x: Math.round(horizontalOffset)
+ y: Math.round(verticalOffset)
+ source: root.source
+ radius: root.radius * Screen.devicePixelRatio
+ samples: root.samples * Screen.devicePixelRatio
+ _thickness: root.spread
+ transparentBorder: root.transparentBorder
+
+
+ _color: root.color;
+ _alphaOnly: true
+ // ignoreDevicePixelRatio: root.ignoreDevicePixelRatio
+
+ ShaderEffect {
+ x: blur._outputRect.x - parent.x
+ y: blur._outputRect.y - parent.y
+ width: transparentBorder ? blur._outputRect.width : blur.width
+ height: transparentBorder ? blur._outputRect.height : blur.height
+ property variant source: blur._output;
+ }
+
+ }
+
+ ShaderEffectSource {
+ id: cacheItem
+ x: -blur._kernelRadius + horizontalOffset
+ y: -blur._kernelRadius + verticalOffset
+ width: blur.width + 2 * blur._kernelRadius
+ height: blur.height + 2 * blur._kernelRadius
+ visible: root.cached
+ smooth: true
+ sourceRect: Qt.rect(-blur._kernelRadius, -blur._kernelRadius, width, height);
+ sourceItem: blur
+ hideSource: visible
+ }
+
+
+}
diff --git a/src/imports/graphicaleffects5/private/FastGlow.qml b/src/imports/graphicaleffects5/private/FastGlow.qml
index 6ec8305..f83a8ca 100644
--- a/src/imports/graphicaleffects5/private/FastGlow.qml
+++ b/src/imports/graphicaleffects5/private/FastGlow.qml
@@ -1,11 +1,11 @@
/****************************************************************************
**
-** Copyright (C) 2020 The Qt Company Ltd.
+** Copyright (C) 2022 The Qt Company Ltd.
** Contact: https://www.qt.io/licensing/
**
-** This file is part of the Qt Graphical Effects module of the Qt Toolkit.
+** This file is part of the Qt Graphical Effects module.
**
-** $QT_BEGIN_LICENSE:BSD$
+** $QT_BEGIN_LICENSE:LGPL$
** Commercial License Usage
** Licensees holding valid commercial Qt licenses may use this file in
** accordance with the commercial license agreement provided with the
@@ -14,35 +14,24 @@
** and conditions see https://www.qt.io/terms-conditions. For further
** information use the contact form at https://www.qt.io/contact-us.
**
-** BSD License Usage
-** Alternatively, you may use this file under the terms of the BSD license
-** as follows:
+** GNU Lesser General Public License Usage
+** Alternatively, this file may be used under the terms of the GNU Lesser
+** General Public License version 3 as published by the Free Software
+** Foundation and appearing in the file LICENSE.LGPL3 included in the
+** packaging of this file. Please review the following information to
+** ensure the GNU Lesser General Public License version 3 requirements
+** will be met: https://www.gnu.org/licenses/lgpl-3.0.html.
**
-** "Redistribution and use in source and binary forms, with or without
-** modification, are permitted provided that the following conditions are
-** met:
-** * Redistributions of source code must retain the above copyright
-** notice, this list of conditions and the following disclaimer.
-** * Redistributions in binary form must reproduce the above copyright
-** notice, this list of conditions and the following disclaimer in
-** the documentation and/or other materials provided with the
-** distribution.
-** * Neither the name of The Qt Company Ltd nor the names of its
-** contributors may be used to endorse or promote products derived
-** from this software without specific prior written permission.
-**
-**
-** THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
-** "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
-** LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
-** A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
-** OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
-** SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
-** LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
-** DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
-** THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
-** (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
-** OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE."
+** GNU General Public License Usage
+** Alternatively, this file may be used under the terms of the GNU
+** General Public License version 2.0 or (at your option) the GNU General
+** Public license version 3 or any later version approved by the KDE Free
+** Qt Foundation. The licenses are as published by the Free Software
+** Foundation and appearing in the file LICENSE.GPL2 and LICENSE.GPL3
+** included in the packaging of this file. Please review the following
+** information to ensure the GNU General Public License requirements will
+** be met: https://www.gnu.org/licenses/gpl-2.0.html and
+** https://www.gnu.org/licenses/gpl-3.0.html.
**
** $QT_END_LICENSE$
**
diff --git a/src/imports/graphicaleffects5/private/FastInnerShadow.qml b/src/imports/graphicaleffects5/private/FastInnerShadow.qml
new file mode 100644
index 0000000..d57a994
--- /dev/null
+++ b/src/imports/graphicaleffects5/private/FastInnerShadow.qml
@@ -0,0 +1,335 @@
+/****************************************************************************
+**
+** Copyright (C) 2022 The Qt Company Ltd.
+** Contact: https://www.qt.io/licensing/
+**
+** This file is part of the Qt Graphical Effects module.
+**
+** $QT_BEGIN_LICENSE:LGPL$
+** Commercial License Usage
+** Licensees holding valid commercial Qt licenses may use this file in
+** accordance with the commercial license agreement provided with the
+** Software or, alternatively, in accordance with the terms contained in
+** a written agreement between you and The Qt Company. For licensing terms
+** and conditions see https://www.qt.io/terms-conditions. For further
+** information use the contact form at https://www.qt.io/contact-us.
+**
+** GNU Lesser General Public License Usage
+** Alternatively, this file may be used under the terms of the GNU Lesser
+** General Public License version 3 as published by the Free Software
+** Foundation and appearing in the file LICENSE.LGPL3 included in the
+** packaging of this file. Please review the following information to
+** ensure the GNU Lesser General Public License version 3 requirements
+** will be met: https://www.gnu.org/licenses/lgpl-3.0.html.
+**
+** GNU General Public License Usage
+** Alternatively, this file may be used under the terms of the GNU
+** General Public License version 2.0 or (at your option) the GNU General
+** Public license version 3 or any later version approved by the KDE Free
+** Qt Foundation. The licenses are as published by the Free Software
+** Foundation and appearing in the file LICENSE.GPL2 and LICENSE.GPL3
+** included in the packaging of this file. Please review the following
+** information to ensure the GNU General Public License requirements will
+** be met: https://www.gnu.org/licenses/gpl-2.0.html and
+** https://www.gnu.org/licenses/gpl-3.0.html.
+**
+** $QT_END_LICENSE$
+**
+****************************************************************************/
+
+import QtQuick
+import Qt5Compat.GraphicalEffects.private
+
+Item {
+ id: rootItem
+ property variant source
+ property real blur: 0.0
+ property real horizontalOffset: 0
+ property real verticalOffset: 0
+ property real spread: 0.0
+ property color color: "black"
+ property bool cached: false
+
+ SourceProxy {
+ id: sourceProxy
+ input: rootItem.source
+ }
+
+ ShaderEffectSource {
+ id: cacheItem
+ anchors.fill: shaderItem
+ visible: rootItem.cached
+ smooth: true
+ sourceItem: shaderItem
+ live: true
+ hideSource: visible
+ }
+
+ property string __internalBlurVertexShader: "qrc:/qt-project.org/imports/Qt5Compat/GraphicalEffects/shaders_ng/fastblur_internal.vert.qsb"
+
+ property string __internalBlurFragmentShader: "qrc:/qt-project.org/imports/Qt5Compat/GraphicalEffects/shaders_ng/fastblur_internal.frag.qsb"
+
+ ShaderEffect {
+ id: level0
+ property variant source: sourceProxy.output
+ property real horizontalOffset: rootItem.horizontalOffset / rootItem.width
+ property real verticalOffset: rootItem.verticalOffset / rootItem.width
+ property color color: rootItem.color
+
+ anchors.fill: parent
+ visible: false
+ smooth: true
+ fragmentShader: "qrc:/qt-project.org/imports/Qt5Compat/GraphicalEffects/shaders_ng/fastinnershadow_level0.frag.qsb"
+ }
+
+ ShaderEffectSource {
+ id: level1
+ width: Math.ceil(shaderItem.width / 32) * 32
+ height: Math.ceil(shaderItem.height / 32) * 32
+ sourceItem: level0
+ hideSource: rootItem.visible
+ smooth: true
+ visible: false
+ }
+
+ ShaderEffect {
+ id: effect1
+ property variant source: level1
+ property real yStep: 1/height
+ property real xStep: 1/width
+ anchors.fill: level2
+ visible: false
+ smooth: true
+ vertexShader: __internalBlurVertexShader
+ fragmentShader: __internalBlurFragmentShader
+ }
+
+ ShaderEffectSource {
+ id: level2
+ width: level1.width / 2
+ height: level1.height / 2
+ sourceItem: effect1
+ hideSource: rootItem.visible
+ visible: false
+ smooth: true
+ }
+
+ ShaderEffect {
+ id: effect2
+ property variant source: level2
+ property real yStep: 1/height
+ property real xStep: 1/width
+ anchors.fill: level3
+ visible: false
+ smooth: true
+ vertexShader: __internalBlurVertexShader
+ fragmentShader: __internalBlurFragmentShader
+ }
+
+ ShaderEffectSource {
+ id: level3
+ width: level2.width / 2
+ height: level2.height / 2
+ sourceItem: effect2
+ hideSource: rootItem.visible
+ visible: false
+ smooth: true
+ }
+
+ ShaderEffect {
+ id: effect3
+ property variant source: level3
+ property real yStep: 1/height
+ property real xStep: 1/width
+ anchors.fill: level4
+ visible: false
+ smooth: true
+ vertexShader: __internalBlurVertexShader
+ fragmentShader: __internalBlurFragmentShader
+ }
+
+ ShaderEffectSource {
+ id: level4
+ width: level3.width / 2
+ height: level3.height / 2
+ sourceItem: effect3
+ hideSource: rootItem.visible
+ visible: false
+ smooth: true
+ }
+
+ ShaderEffect {
+ id: effect4
+ property variant source: level4
+ property real yStep: 1/height
+ property real xStep: 1/width
+ anchors.fill: level5
+ visible: false
+ smooth: true
+ vertexShader: __internalBlurVertexShader
+ fragmentShader: __internalBlurFragmentShader
+ }
+
+ ShaderEffectSource {
+ id: level5
+ width: level4.width / 2
+ height: level4.height / 2
+ sourceItem: effect4
+ hideSource: rootItem.visible
+ visible: false
+ smooth: true
+ }
+
+ ShaderEffect {
+ id: effect5
+ property variant source: level5
+ property real yStep: 1/height
+ property real xStep: 1/width
+ anchors.fill: level6
+ visible: false
+ smooth: true
+ vertexShader: __internalBlurVertexShader
+ fragmentShader: __internalBlurFragmentShader
+ }
+
+ ShaderEffectSource {
+ id: level6
+ width: level5.width / 2
+ height: level5.height / 2
+ sourceItem: effect5
+ hideSource: rootItem.visible
+ visible: false
+ smooth: true
+ }
+
+ Item {
+ id: dummysource
+ width: 1
+ height: 1
+ visible: false
+ }
+
+ ShaderEffectSource {
+ id: dummy
+ width: 1
+ height: 1
+ sourceItem: dummysource
+ visible: false
+ smooth: false
+ live: false
+ }
+
+ ShaderEffect {
+ id: shaderItem
+ width: parent.width
+ height: parent.height
+
+ property variant original: sourceProxy.output
+ property variant source1: level1
+ property variant source2: level2
+ property variant source3: level3
+ property variant source4: level4
+ property variant source5: level5
+ property variant source6: level6
+ property real lod: rootItem.blur
+
+ property real weight1;
+ property real weight2;
+ property real weight3;
+ property real weight4;
+ property real weight5;
+ property real weight6;
+
+ property real spread: 1.0 - (rootItem.spread * 0.98)
+ property color color: rootItem.color
+
+ function weight(v) {
+ if (v <= 0.0)
+ return 1
+ if (v >= 0.5)
+ return 0
+
+ return 1.0 - v / 0.5
+ }
+
+ function calculateWeights() {
+
+ var w1 = weight(Math.abs(lod - 0.100))
+ var w2 = weight(Math.abs(lod - 0.300))
+ var w3 = weight(Math.abs(lod - 0.500))
+ var w4 = weight(Math.abs(lod - 0.700))
+ var w5 = weight(Math.abs(lod - 0.900))
+ var w6 = weight(Math.abs(lod - 1.100))
+
+ var sum = w1 + w2 + w3 + w4 + w5 + w6;
+ weight1 = w1 / sum;
+ weight2 = w2 / sum;
+ weight3 = w3 / sum;
+ weight4 = w4 / sum;
+ weight5 = w5 / sum;
+ weight6 = w6 / sum;
+
+ upateSources()
+ }
+
+ function upateSources() {
+ var sources = new Array();
+ var weights = new Array();
+
+ if (weight1 > 0) {
+ sources.push(level1)
+ weights.push(weight1)
+ }
+
+ if (weight2 > 0) {
+ sources.push(level2)
+ weights.push(weight2)
+ }
+
+ if (weight3 > 0) {
+ sources.push(level3)
+ weights.push(weight3)
+ }
+
+ if (weight4 > 0) {
+ sources.push(level4)
+ weights.push(weight4)
+ }
+
+ if (weight5 > 0) {
+ sources.push(level5)
+ weights.push(weight5)
+ }
+
+ if (weight6 > 0) {
+ sources.push(level6)
+ weights.push(weight6)
+ }
+
+ for (var j = sources.length; j < 6; j++) {
+ sources.push(dummy)
+ weights.push(0.0)
+ }
+
+ source1 = sources[0]
+ source2 = sources[1]
+ source3 = sources[2]
+ source4 = sources[3]
+ source5 = sources[4]
+ source6 = sources[5]
+
+ weight1 = weights[0]
+ weight2 = weights[1]
+ weight3 = weights[2]
+ weight4 = weights[3]
+ weight5 = weights[4]
+ weight6 = weights[5]
+ }
+
+ Component.onCompleted: calculateWeights()
+
+ onLodChanged: calculateWeights()
+
+ fragmentShader: "qrc:/qt-project.org/imports/Qt5Compat/GraphicalEffects/shaders_ng/fastinnershadow.frag.qsb"
+ }
+}
diff --git a/src/imports/graphicaleffects5/private/GaussianDirectionalBlur.qml b/src/imports/graphicaleffects5/private/GaussianDirectionalBlur.qml
new file mode 100644
index 0000000..f1dbc1c
--- /dev/null
+++ b/src/imports/graphicaleffects5/private/GaussianDirectionalBlur.qml
@@ -0,0 +1,295 @@
+/****************************************************************************
+**
+** Copyright (C) 2022 The Qt Company Ltd.
+** Contact: https://www.qt.io/licensing/
+**
+** This file is part of the Qt Graphical Effects module.
+**
+** $QT_BEGIN_LICENSE:LGPL$
+** Commercial License Usage
+** Licensees holding valid commercial Qt licenses may use this file in
+** accordance with the commercial license agreement provided with the
+** Software or, alternatively, in accordance with the terms contained in
+** a written agreement between you and The Qt Company. For licensing terms
+** and conditions see https://www.qt.io/terms-conditions. For further
+** information use the contact form at https://www.qt.io/contact-us.
+**
+** GNU Lesser General Public License Usage
+** Alternatively, this file may be used under the terms of the GNU Lesser
+** General Public License version 3 as published by the Free Software
+** Foundation and appearing in the file LICENSE.LGPL3 included in the
+** packaging of this file. Please review the following information to
+** ensure the GNU Lesser General Public License version 3 requirements
+** will be met: https://www.gnu.org/licenses/lgpl-3.0.html.
+**
+** GNU General Public License Usage
+** Alternatively, this file may be used under the terms of the GNU
+** General Public License version 2.0 or (at your option) the GNU General
+** Public license version 3 or any later version approved by the KDE Free
+** Qt Foundation. The licenses are as published by the Free Software
+** Foundation and appearing in the file LICENSE.GPL2 and LICENSE.GPL3
+** included in the packaging of this file. Please review the following
+** information to ensure the GNU General Public License requirements will
+** be met: https://www.gnu.org/licenses/gpl-2.0.html and
+** https://www.gnu.org/licenses/gpl-3.0.html.
+**
+** $QT_END_LICENSE$
+**
+****************************************************************************/
+
+import QtQuick
+import Qt5Compat.GraphicalEffects.private
+
+Item {
+ id: rootItem
+ property variant source
+ property real deviation: (radius + 1) / 3.3333
+ property real radius: 0.0
+ property int maximumRadius: 0
+ property real horizontalStep: 0.0
+ property real verticalStep: 0.0
+ property bool transparentBorder: false
+ property bool cached: false
+
+ property bool enableColor: false
+ property color color: "white"
+ property real spread: 0.0
+
+ property bool enableMask: false
+ property variant maskSource
+
+ SourceProxy {
+ id: sourceProxy
+ input: rootItem.source
+ }
+
+ SourceProxy {
+ id: maskSourceProxy
+ input: rootItem.maskSource
+ }
+
+ ShaderEffectSource {
+ id: cacheItem
+ anchors.fill: rootItem
+ visible: rootItem.cached
+ smooth: true
+ sourceItem: shaderItem
+ live: true
+ hideSource: visible
+ }
+
+ ShaderBuilder {
+ id: shaderBuilder
+ }
+
+ ShaderEffect {
+ id: shaderItem
+ property variant source: sourceProxy.output
+ property real deviation: Math.max(0.1, rootItem.deviation)
+ property real radius: rootItem.radius
+ property int maxRadius: rootItem.maximumRadius
+ property bool transparentBorder: rootItem.transparentBorder
+ property real gaussianSum: 0.0
+ property real startIndex: 0.0
+ property real deltaFactor: (2 * radius - 1) / (maxRadius * 2 - 1)
+ property real expandX: transparentBorder && rootItem.horizontalStep > 0 ? maxRadius / width : 0.0
+ property real expandY: transparentBorder && rootItem.verticalStep > 0 ? maxRadius / height : 0.0
+ property variant gwts: []
+ property variant delta: Qt.vector3d(rootItem.horizontalStep * deltaFactor, rootItem.verticalStep * deltaFactor, startIndex);
+ property variant factor_0_2: Qt.vector3d(gwts[0], gwts[1], gwts[2]);
+ property variant factor_3_5: Qt.vector3d(gwts[3], gwts[4], gwts[5]);
+ property variant factor_6_8: Qt.vector3d(gwts[6], gwts[7], gwts[8]);
+ property variant factor_9_11: Qt.vector3d(gwts[9], gwts[10], gwts[11]);
+ property variant factor_12_14: Qt.vector3d(gwts[12], gwts[13], gwts[14]);
+ property variant factor_15_17: Qt.vector3d(gwts[15], gwts[16], gwts[17]);
+ property variant factor_18_20: Qt.vector3d(gwts[18], gwts[19], gwts[20]);
+ property variant factor_21_23: Qt.vector3d(gwts[21], gwts[22], gwts[23]);
+ property variant factor_24_26: Qt.vector3d(gwts[24], gwts[25], gwts[26]);
+ property variant factor_27_29: Qt.vector3d(gwts[27], gwts[28], gwts[29]);
+ property variant factor_30_31: Qt.point(gwts[30], gwts[31]);
+
+ property color color: rootItem.color
+ property real spread: 1.0 - (rootItem.spread * 0.98)
+ property variant maskSource: maskSourceProxy.output
+
+ anchors.fill: rootItem
+
+ function gausFunc(x){
+ //Gaussian function = h(x):=(1/sqrt(2*3.14159*(D^2))) * %e^(-(x^2)/(2*(D^2)));
+ return (1.0 / Math.sqrt(2 * Math.PI * (Math.pow(shaderItem.deviation, 2)))) * Math.pow(Math.E, -((Math.pow(x, 2)) / (2 * (Math.pow(shaderItem.deviation, 2)))));
+ }
+
+ function updateGaussianWeights() {
+ gaussianSum = 0.0;
+ startIndex = -maxRadius + 0.5
+
+ var n = new Array(32);
+ for (var j = 0; j < 32; j++)
+ n[j] = 0;
+
+ var max = maxRadius * 2
+ var delta = (2 * radius - 1) / (max - 1);
+ for (var i = 0; i < max; i++) {
+ n[i] = gausFunc(-radius + 0.5 + i * delta);
+ gaussianSum += n[i];
+ }
+
+ gwts = n;
+ }
+
+ function buildFragmentShader() {
+
+ var shaderSteps = [
+ "fragColor += texture(source, texCoord) * factor_0_2.x; texCoord += shift;",
+ "fragColor += texture(source, texCoord) * factor_0_2.y; texCoord += shift;",
+ "fragColor += texture(source, texCoord) * factor_0_2.z; texCoord += shift;",
+
+ "fragColor += texture(source, texCoord) * factor_3_5.x; texCoord += shift;",
+ "fragColor += texture(source, texCoord) * factor_3_5.y; texCoord += shift;",
+ "fragColor += texture(source, texCoord) * factor_3_5.z; texCoord += shift;",
+
+ "fragColor += texture(source, texCoord) * factor_6_8.x; texCoord += shift;",
+ "fragColor += texture(source, texCoord) * factor_6_8.y; texCoord += shift;",
+ "fragColor += texture(source, texCoord) * factor_6_8.z; texCoord += shift;",
+
+ "fragColor += texture(source, texCoord) * factor_9_11.x; texCoord += shift;",
+ "fragColor += texture(source, texCoord) * factor_9_11.y; texCoord += shift;",
+ "fragColor += texture(source, texCoord) * factor_9_11.z; texCoord += shift;",
+
+ "fragColor += texture(source, texCoord) * factor_12_14.x; texCoord += shift;",
+ "fragColor += texture(source, texCoord) * factor_12_14.y; texCoord += shift;",
+ "fragColor += texture(source, texCoord) * factor_12_14.z; texCoord += shift;",
+
+ "fragColor += texture(source, texCoord) * factor_15_17.x; texCoord += shift;",
+ "fragColor += texture(source, texCoord) * factor_15_17.y; texCoord += shift;",
+ "fragColor += texture(source, texCoord) * factor_15_17.z; texCoord += shift;",
+
+ "fragColor += texture(source, texCoord) * factor_18_20.x; texCoord += shift;",
+ "fragColor += texture(source, texCoord) * factor_18_20.y; texCoord += shift;",
+ "fragColor += texture(source, texCoord) * factor_18_20.z; texCoord += shift;",
+
+ "fragColor += texture(source, texCoord) * factor_21_23.x; texCoord += shift;",
+ "fragColor += texture(source, texCoord) * factor_21_23.y; texCoord += shift;",
+ "fragColor += texture(source, texCoord) * factor_21_23.z; texCoord += shift;",
+
+ "fragColor += texture(source, texCoord) * factor_24_26.x; texCoord += shift;",
+ "fragColor += texture(source, texCoord) * factor_24_26.y; texCoord += shift;",
+ "fragColor += texture(source, texCoord) * factor_24_26.z; texCoord += shift;",
+
+ "fragColor += texture(source, texCoord) * factor_27_29.x; texCoord += shift;",
+ "fragColor += texture(source, texCoord) * factor_27_29.y; texCoord += shift;",
+ "fragColor += texture(source, texCoord) * factor_27_29.z; texCoord += shift;",
+
+ "fragColor += texture(source, texCoord) * factor_30_31.x; texCoord += shift;",
+ "fragColor += texture(source, texCoord) * factor_30_31.y; texCoord += shift;"
+ ]
+
+ var shader = fragmentShaderBegin
+ var samples = maxRadius * 2
+ if (samples > 32) {
+ console.log("DirectionalGaussianBlur.qml WARNING: Maximum of blur radius (16) exceeded!")
+ samples = 32
+ }
+
+ for (var i = 0; i < samples; i++) {
+ shader += shaderSteps[i]
+ }
+
+ shader += fragmentShaderEnd
+
+ var colorizeSteps = ""
+ var colorizeUniforms = ""
+
+ var maskSteps = ""
+ var maskUniforms = ""
+
+ if (enableColor) {
+ colorizeSteps += "fragColor = mix(vec4(0), color, clamp((fragColor.a - 0.0) / (spread - 0.0), 0.0, 1.0));\n"
+ colorizeUniforms += "vec4 color;\n"
+ colorizeUniforms += "float spread;\n"
+ }
+
+ if (enableMask) {
+ maskSteps += "shift *= texture(maskSource, qt_TexCoord0).a;\n"
+ maskUniforms += "layout(binding = 2) uniform sampler2D maskSource;\n"
+ }
+
+ shader = shader.replace("PLACEHOLDER_COLORIZE_STEPS", colorizeSteps)
+ shader = shader.replace("PLACEHOLDER_COLORIZE_UNIFORMS", colorizeUniforms)
+ shader = shader.replace("PLACEHOLDER_MASK_STEPS", maskSteps)
+ shader = shader.replace("PLACEHOLDER_MASK_UNIFORMS", maskUniforms)
+
+ fragmentShader = shaderBuilder.buildFragmentShader(shader)
+ }
+
+ onDeviationChanged: updateGaussianWeights()
+
+ onRadiusChanged: updateGaussianWeights()
+
+ onTransparentBorderChanged: {
+ buildFragmentShader()
+ updateGaussianWeights()
+ }
+
+ onMaxRadiusChanged: {
+ buildFragmentShader()
+ updateGaussianWeights()
+ }
+
+ Component.onCompleted: {
+ buildFragmentShader()
+ updateGaussianWeights()
+ }
+
+ property string fragmentShaderBegin: "#version 440
+ layout(location = 0) in vec2 qt_TexCoord0;
+ layout(location = 0) out vec4 fragColor;
+
+ layout(std140, binding = 0) uniform buf {
+ mat4 qt_Matrix;
+ float qt_Opacity;
+ vec3 delta;
+ vec3 factor_0_2;
+ vec3 factor_3_5;
+ vec3 factor_6_8;
+ vec3 factor_9_11;
+ vec3 factor_12_14;
+ vec3 factor_15_17;
+ vec3 factor_18_20;
+ vec3 factor_21_23;
+ vec3 factor_24_26;
+ vec3 factor_27_29;
+ vec2 factor_30_31;
+ float gaussianSum;
+ float expandX;
+ float expandY;
+ PLACEHOLDER_COLORIZE_UNIFORMS
+ };
+ layout(binding = 1) uniform sampler2D source;
+ PLACEHOLDER_MASK_UNIFORMS
+
+ void main() {
+ vec2 shift = vec2(delta.x, delta.y);
+
+ PLACEHOLDER_MASK_STEPS
+
+ float index = delta.z;
+ vec2 texCoord = qt_TexCoord0;
+ texCoord.s = (texCoord.s - expandX) / (1.0 - 2.0 * expandX);
+ texCoord.t = (texCoord.t - expandY) / (1.0 - 2.0 * expandY);
+ texCoord += (shift * index);
+
+ fragColor = vec4(0.0, 0.0, 0.0, 0.0);
+ "
+
+ property string fragmentShaderEnd: "
+
+ fragColor /= gaussianSum;
+
+ PLACEHOLDER_COLORIZE_STEPS
+
+ fragColor *= qt_Opacity;
+ }
+ "
+ }
+}
diff --git a/src/imports/graphicaleffects5/private/GaussianGlow.qml b/src/imports/graphicaleffects5/private/GaussianGlow.qml
new file mode 100644
index 0000000..d2af242
--- /dev/null
+++ b/src/imports/graphicaleffects5/private/GaussianGlow.qml
@@ -0,0 +1,98 @@
+/****************************************************************************
+**
+** Copyright (C) 2017 The Qt Company Ltd.
+** Contact: https://www.qt.io/licensing/
+**
+** This file is part of the Qt Graphical Effects module.
+**
+** $QT_BEGIN_LICENSE:LGPL$
+** Commercial License Usage
+** Licensees holding valid commercial Qt licenses may use this file in
+** accordance with the commercial license agreement provided with the
+** Software or, alternatively, in accordance with the terms contained in
+** a written agreement between you and The Qt Company. For licensing terms
+** and conditions see https://www.qt.io/terms-conditions. For further
+** information use the contact form at https://www.qt.io/contact-us.
+**
+** GNU Lesser General Public License Usage
+** Alternatively, this file may be used under the terms of the GNU Lesser
+** General Public License version 3 as published by the Free Software
+** Foundation and appearing in the file LICENSE.LGPL3 included in the
+** packaging of this file. Please review the following information to
+** ensure the GNU Lesser General Public License version 3 requirements
+** will be met: https://www.gnu.org/licenses/lgpl-3.0.html.
+**
+** GNU General Public License Usage
+** Alternatively, this file may be used under the terms of the GNU
+** General Public License version 2.0 or (at your option) the GNU General
+** Public license version 3 or any later version approved by the KDE Free
+** Qt Foundation. The licenses are as published by the Free Software
+** Foundation and appearing in the file LICENSE.GPL2 and LICENSE.GPL3
+** included in the packaging of this file. Please review the following
+** information to ensure the GNU General Public License requirements will
+** be met: https://www.gnu.org/licenses/gpl-2.0.html and
+** https://www.gnu.org/licenses/gpl-3.0.html.
+**
+** $QT_END_LICENSE$
+**
+****************************************************************************/
+
+import QtQuick
+import Qt5Compat.GraphicalEffects.private
+
+Item {
+ id: rootItem
+ property variant source
+ property real radius: 0.0
+ property int maximumRadius: 0
+ property real spread: 0.0
+ property color color: "white"
+ property bool cached: false
+ property bool transparentBorder: false
+
+ SourceProxy {
+ id: sourceProxy
+ input: rootItem.source
+ sourceRect: rootItem.transparentBorder ? Qt.rect(-1, -1, parent.width + 2.0, parent.height + 2.0) : Qt.rect(0, 0, 0, 0)
+ }
+
+ ShaderEffectSource {
+ id: cacheItem
+ anchors.fill: shaderItem
+ visible: rootItem.cached
+ smooth: true
+ sourceItem: shaderItem
+ live: true
+ hideSource: visible
+ }
+
+ GaussianDirectionalBlur {
+ id: shaderItem
+ x: transparentBorder ? -maximumRadius - 1 : 0
+ y: transparentBorder ? -maximumRadius - 1 : 0
+ width: horizontalBlur.width
+ height: horizontalBlur.height
+ horizontalStep: 0.0
+ verticalStep: 1.0 / parent.height
+ source: horizontalBlur
+ radius: rootItem.radius
+ maximumRadius: rootItem.maximumRadius
+ transparentBorder: rootItem.transparentBorder
+ enableColor: true
+ color: rootItem.color
+ spread: rootItem.spread
+ }
+
+ GaussianDirectionalBlur {
+ id: horizontalBlur
+ width: transparentBorder ? parent.width + 2 * maximumRadius + 2 : parent.width
+ height: transparentBorder ? parent.height + 2 * maximumRadius + 2 : parent.height
+ horizontalStep: 1.0 / parent.width
+ verticalStep: 0.0
+ source: sourceProxy.output
+ radius: rootItem.radius
+ maximumRadius: rootItem.maximumRadius
+ transparentBorder: rootItem.transparentBorder
+ visible: false
+ }
+}
diff --git a/src/imports/graphicaleffects5/private/GaussianInnerShadow.qml b/src/imports/graphicaleffects5/private/GaussianInnerShadow.qml
new file mode 100644
index 0000000..f47cf08
--- /dev/null
+++ b/src/imports/graphicaleffects5/private/GaussianInnerShadow.qml
@@ -0,0 +1,123 @@
+/****************************************************************************
+**
+** Copyright (C) 2022 The Qt Company Ltd.
+** Contact: https://www.qt.io/licensing/
+**
+** This file is part of the Qt Graphical Effects module.
+**
+** $QT_BEGIN_LICENSE:LGPL$
+** Commercial License Usage
+** Licensees holding valid commercial Qt licenses may use this file in
+** accordance with the commercial license agreement provided with the
+** Software or, alternatively, in accordance with the terms contained in
+** a written agreement between you and The Qt Company. For licensing terms
+** and conditions see https://www.qt.io/terms-conditions. For further
+** information use the contact form at https://www.qt.io/contact-us.
+**
+** GNU Lesser General Public License Usage
+** Alternatively, this file may be used under the terms of the GNU Lesser
+** General Public License version 3 as published by the Free Software
+** Foundation and appearing in the file LICENSE.LGPL3 included in the
+** packaging of this file. Please review the following information to
+** ensure the GNU Lesser General Public License version 3 requirements
+** will be met: https://www.gnu.org/licenses/lgpl-3.0.html.
+**
+** GNU General Public License Usage
+** Alternatively, this file may be used under the terms of the GNU
+** General Public License version 2.0 or (at your option) the GNU General
+** Public license version 3 or any later version approved by the KDE Free
+** Qt Foundation. The licenses are as published by the Free Software
+** Foundation and appearing in the file LICENSE.GPL2 and LICENSE.GPL3
+** included in the packaging of this file. Please review the following
+** information to ensure the GNU General Public License requirements will
+** be met: https://www.gnu.org/licenses/gpl-2.0.html and
+** https://www.gnu.org/licenses/gpl-3.0.html.
+**
+** $QT_END_LICENSE$
+**
+****************************************************************************/
+
+import QtQuick
+import Qt5Compat.GraphicalEffects.private
+
+Item {
+ id: rootItem
+ property variant source
+ property real radius: 0.0
+ property int maximumRadius: 0
+ property real horizontalOffset: 0
+ property real verticalOffset: 0
+ property real spread: 0
+ property color color: "black"
+ property bool cached: false
+
+ SourceProxy {
+ id: sourceProxy
+ input: rootItem.source
+ }
+
+ ShaderEffectSource {
+ id: cacheItem
+ anchors.fill: shaderItem
+ visible: rootItem.cached
+ smooth: true
+ sourceItem: shaderItem
+ live: true
+ hideSource: visible
+ }
+
+ ShaderEffect{
+ id: shadowItem
+ anchors.fill: parent
+
+ property variant original: sourceProxy.output
+ property color color: rootItem.color
+ property real horizontalOffset: rootItem.horizontalOffset / rootItem.width
+ property real verticalOffset: rootItem.verticalOffset / rootItem.height
+
+ visible: false
+ fragmentShader: "qrc:/qt-project.org/imports/Qt5Compat/GraphicalEffects/shaders_ng/gaussianinnershadow_shadow.frag.qsb"
+ }
+
+ GaussianDirectionalBlur {
+ id: blurItem
+ anchors.fill: parent
+ horizontalStep: 0.0
+ verticalStep: 1.0 / parent.height
+ source: horizontalBlur
+ radius: rootItem.radius
+ maximumRadius: rootItem.maximumRadius
+ visible: false
+ }
+
+ GaussianDirectionalBlur {
+ id: horizontalBlur
+ width: transparentBorder ? parent.width + 2 * maximumRadius : parent.width
+ height: parent.height
+ horizontalStep: 1.0 / parent.width
+ verticalStep: 0.0
+ source: shadowItem
+ radius: rootItem.radius
+ maximumRadius: rootItem.maximumRadius
+ visible: false
+ }
+
+ ShaderEffectSource {
+ id: blurredSource
+ sourceItem: blurItem
+ live: true
+ smooth: true
+ }
+
+ ShaderEffect {
+ id: shaderItem
+ anchors.fill: parent
+
+ property variant original: sourceProxy.output
+ property variant shadow: blurredSource
+ property real spread: 1.0 - (rootItem.spread * 0.98)
+ property color color: rootItem.color
+
+ fragmentShader: "qrc:/qt-project.org/imports/Qt5Compat/GraphicalEffects/shaders_ng/gaussianinnershadow.frag.qsb"
+ }
+}
diff --git a/src/imports/graphicaleffects5/private/GaussianMaskedBlur.qml b/src/imports/graphicaleffects5/private/GaussianMaskedBlur.qml
new file mode 100644
index 0000000..8c86dd2
--- /dev/null
+++ b/src/imports/graphicaleffects5/private/GaussianMaskedBlur.qml
@@ -0,0 +1,104 @@
+/****************************************************************************
+**
+** Copyright (C) 2022 The Qt Company Ltd.
+** Contact: https://www.qt.io/licensing/
+**
+** This file is part of the Qt Graphical Effects module.
+**
+** $QT_BEGIN_LICENSE:LGPL$
+** Commercial License Usage
+** Licensees holding valid commercial Qt licenses may use this file in
+** accordance with the commercial license agreement provided with the
+** Software or, alternatively, in accordance with the terms contained in
+** a written agreement between you and The Qt Company. For licensing terms
+** and conditions see https://www.qt.io/terms-conditions. For further
+** information use the contact form at https://www.qt.io/contact-us.
+**
+** GNU Lesser General Public License Usage
+** Alternatively, this file may be used under the terms of the GNU Lesser
+** General Public License version 3 as published by the Free Software
+** Foundation and appearing in the file LICENSE.LGPL3 included in the
+** packaging of this file. Please review the following information to
+** ensure the GNU Lesser General Public License version 3 requirements
+** will be met: https://www.gnu.org/licenses/lgpl-3.0.html.
+**
+** GNU General Public License Usage
+** Alternatively, this file may be used under the terms of the GNU
+** General Public License version 2.0 or (at your option) the GNU General
+** Public license version 3 or any later version approved by the KDE Free
+** Qt Foundation. The licenses are as published by the Free Software
+** Foundation and appearing in the file LICENSE.GPL2 and LICENSE.GPL3
+** included in the packaging of this file. Please review the following
+** information to ensure the GNU General Public License requirements will
+** be met: https://www.gnu.org/licenses/gpl-2.0.html and
+** https://www.gnu.org/licenses/gpl-3.0.html.
+**
+** $QT_END_LICENSE$
+**
+****************************************************************************/
+
+import QtQuick
+import Qt5Compat.GraphicalEffects.private
+
+Item {
+ id: rootItem
+ property variant source
+ property variant maskSource
+ property real radius: 0.0
+ property int maximumRadius: 0
+ property bool cached: false
+ property bool transparentBorder: false
+
+ SourceProxy {
+ id: sourceProxy
+ input: rootItem.source
+ sourceRect: rootItem.transparentBorder ? Qt.rect(-1, -1, parent.width + 2.0, parent.height + 2.0) : Qt.rect(0, 0, 0, 0)
+ }
+
+ SourceProxy {
+ id: maskSourceProxy
+ input: rootItem.maskSource
+ sourceRect: rootItem.transparentBorder ? Qt.rect(-1, -1, parent.width + 2.0, parent.height + 2.0) : Qt.rect(0, 0, 0, 0)
+ }
+
+ ShaderEffectSource {
+ id: cacheItem
+ anchors.fill: blur
+ visible: rootItem.cached
+ smooth: true
+ sourceItem: blur
+ live: true
+ hideSource: visible
+ }
+
+ GaussianDirectionalBlur {
+ id: blur
+ x: transparentBorder ? -maximumRadius - 1: 0
+ y: transparentBorder ? -maximumRadius - 1: 0
+ width: horizontalBlur.width
+ height: horizontalBlur.height
+ horizontalStep: 0.0
+ verticalStep: 1.0 / parent.height
+ source: horizontalBlur
+ enableMask: true
+ maskSource: maskSourceProxy.output
+ radius: rootItem.radius
+ maximumRadius: rootItem.maximumRadius
+ transparentBorder: rootItem.transparentBorder
+ }
+
+ GaussianDirectionalBlur {
+ id: horizontalBlur
+ width: transparentBorder ? parent.width + 2 * maximumRadius + 2 : parent.width
+ height: transparentBorder ? parent.height + 2 * maximumRadius + 2 : parent.height
+ horizontalStep: 1.0 / parent.width
+ verticalStep: 0.0
+ source: sourceProxy.output
+ enableMask: true
+ maskSource: maskSourceProxy.output
+ radius: rootItem.radius
+ maximumRadius: rootItem.maximumRadius
+ transparentBorder: rootItem.transparentBorder
+ visible: false
+ }
+}
diff --git a/src/imports/graphicaleffects5/private/plugin.cpp b/src/imports/graphicaleffects5/private/plugin.cpp
index 26d3716..1329674 100644
--- a/src/imports/graphicaleffects5/private/plugin.cpp
+++ b/src/imports/graphicaleffects5/private/plugin.cpp
@@ -52,6 +52,7 @@
#include <QtQml/qqml.h>
#include <QtQml/qqmlengine.h>
+#include "qgfxshaderbuilder_p.h"
#include "qgfxsourceproxy_p.h"
QT_BEGIN_NAMESPACE
@@ -67,6 +68,7 @@ public:
{
Q_ASSERT(QByteArray(uri) == QByteArrayLiteral("Qt5Compat.GraphicalEffects.private"));
qmlRegisterType<QGfxSourceProxy>(uri, 1, 0, "SourceProxy");
+ qmlRegisterType<QGfxShaderBuilder>(uri, 1, 0, "ShaderBuilder");
qmlRegisterModule(uri, QT_VERSION_MAJOR, QT_VERSION_MINOR);
}
diff --git a/src/imports/graphicaleffects5/private/qgfxshaderbuilder.cpp b/src/imports/graphicaleffects5/private/qgfxshaderbuilder.cpp
new file mode 100644
index 0000000..3e2ff32
--- /dev/null
+++ b/src/imports/graphicaleffects5/private/qgfxshaderbuilder.cpp
@@ -0,0 +1,519 @@
+/****************************************************************************
+**
+** Copyright (C) 2016 Jolla Ltd, author: <gunnar.sletta@jollamobile.com>
+** Copyright (C) 2022 The Qt Company Ltd.
+** Contact: http://www.qt-project.org/legal
+**
+** This file is part of the Qt Graphical Effects module of the Qt Toolkit.
+**
+** $QT_BEGIN_LICENSE:LGPL$
+** Commercial License Usage
+** Licensees holding valid commercial Qt licenses may use this file in
+** accordance with the commercial license agreement provided with the
+** Software or, alternatively, in accordance with the terms contained in
+** a written agreement between you and The Qt Company. For licensing terms
+** and conditions see https://www.qt.io/terms-conditions. For further
+** information use the contact form at https://www.qt.io/contact-us.
+**
+** GNU Lesser General Public License Usage
+** Alternatively, this file may be used under the terms of the GNU Lesser
+** General Public License version 3 as published by the Free Software
+** Foundation and appearing in the file LICENSE.LGPL3 included in the
+** packaging of this file. Please review the following information to
+** ensure the GNU Lesser General Public License version 3 requirements
+** will be met: https://www.gnu.org/licenses/lgpl-3.0.html.
+**
+** GNU General Public License Usage
+** Alternatively, this file may be used under the terms of the GNU
+** General Public License version 2.0 or (at your option) the GNU General
+** Public license version 3 or any later version approved by the KDE Free
+** Qt Foundation. The licenses are as published by the Free Software
+** Foundation and appearing in the file LICENSE.GPL2 and LICENSE.GPL3
+** included in the packaging of this file. Please review the following
+** information to ensure the GNU General Public License requirements will
+** be met: https://www.gnu.org/licenses/gpl-2.0.html and
+** https://www.gnu.org/licenses/gpl-3.0.html.
+**
+** $QT_END_LICENSE$
+**
+****************************************************************************/
+
+#include "qgfxshaderbuilder_p.h"
+
+#include <QtCore/QDebug>
+#include <QtCore/QUrl>
+#include <QtCore/QTemporaryFile>
+#include <QtGui/QOffscreenSurface>
+#include <QtGui/QOpenGLContext>
+#include <QtGui/QOpenGLFunctions>
+
+#include <QtShaderTools/private/qshaderbaker_p.h>
+#include <QtQuick/qquickwindow.h>
+
+#include <qmath.h>
+#include <qnumeric.h>
+
+#ifndef GL_MAX_VARYING_COMPONENTS
+#define GL_MAX_VARYING_COMPONENTS 0x8B4B
+#endif
+
+#ifndef GL_MAX_VARYING_FLOATS
+#define GL_MAX_VARYING_FLOATS 0x8B4B
+#endif
+
+#ifndef GL_MAX_VARYING_VECTORS
+#define GL_MAX_VARYING_VECTORS 0x8DFC
+#endif
+
+#if !defined(QT5COMPAT_MAX_BLUR_SAMPLES)
+#define QT5COMPAT_MAX_BLUR_SAMPLES 15 // Conservative estimate for maximum varying vectors in
+ // shaders (maximum 60 components on some Metal
+ // implementations, hence 15 vectors of 4 components each)
+#elif !defined(QT5COMPAT_MAX_BLUR_SAMPLES_GL)
+#define QT5COMPAT_MAX_BLUR_SAMPLES_GL QT5COMPAT_MAX_BLUR_SAMPLES
+#endif
+
+#if !defined(QT5COMPAT_MAX_BLUR_SAMPLES_GL)
+#define QT5COMPAT_MAX_BLUR_SAMPLES_GL 8 // minimum number of varyings in the ES 2.0 spec.
+#endif
+
+QGfxShaderBuilder::QGfxShaderBuilder()
+{
+ QList<QShaderBaker::GeneratedShader> targets;
+
+ QSGRendererInterface::GraphicsApi graphicsApi = QQuickWindow::graphicsApi();
+ switch (graphicsApi) {
+ case QSGRendererInterface::Direct3D11:
+ targets.append({ QShader::HlslShader, QShaderVersion(50) });
+ break;
+ case QSGRendererInterface::OpenGL:
+ targets.append({ QShader::GlslShader, QShaderVersion(100, QShaderVersion::GlslEs) });
+ targets.append({ QShader::GlslShader, QShaderVersion(120) });
+ targets.append({ QShader::GlslShader, QShaderVersion(150) });
+ break;
+ case QSGRendererInterface::Metal:
+ targets.append({ QShader::MslShader, QShaderVersion(12) });
+ break;
+ case QSGRendererInterface::Vulkan:
+ targets.append({ QShader::SpirvShader, QShaderVersion(100) });
+ break;
+ default:
+ qWarning("QGfxShaderBuilder: Unsupported graphics backend. No shaders will be generated.");
+ break;
+ }
+
+ m_shaderBaker.setGeneratedShaders(targets);
+ m_shaderBaker.setGeneratedShaderVariants({ QShader::StandardShader,
+ QShader::BatchableVertexShader });
+
+#ifndef QT_NO_OPENGL
+ if (graphicsApi == QSGRendererInterface::OpenGL) {
+ // The following code makes the assumption that an OpenGL context the GUI
+ // thread will get the same capabilities as the render thread's OpenGL
+ // context. Not 100% accurate, but it works...
+ QOpenGLContext context;
+ if (!context.create()) {
+ qDebug() << "failed to acquire GL context to resolve capabilities, using defaults..";
+ m_maxBlurSamples = QT5COMPAT_MAX_BLUR_SAMPLES_GL;
+ return;
+ }
+
+ QOffscreenSurface surface;
+ // In very odd cases, we can get incompatible configs here unless we pass the
+ // GL context's format on to the offscreen format.
+ surface.setFormat(context.format());
+ surface.create();
+
+ QOpenGLContext *oldContext = QOpenGLContext::currentContext();
+ QSurface *oldSurface = oldContext ? oldContext->surface() : 0;
+ if (context.makeCurrent(&surface)) {
+ QOpenGLFunctions *gl = context.functions();
+ if (context.isOpenGLES()) {
+ gl->glGetIntegerv(GL_MAX_VARYING_VECTORS, &m_maxBlurSamples);
+ } else if (context.format().majorVersion() >= 3) {
+ int components;
+ gl->glGetIntegerv(GL_MAX_VARYING_COMPONENTS, &components);
+ m_maxBlurSamples = components / 2.0;
+ } else {
+ int floats;
+ gl->glGetIntegerv(GL_MAX_VARYING_FLOATS, &floats);
+ m_maxBlurSamples = floats / 2.0;
+ }
+ if (oldContext && oldSurface)
+ oldContext->makeCurrent(oldSurface);
+ else
+ context.doneCurrent();
+ } else {
+ qDebug() << "QGfxShaderBuilder: Failed to acquire GL context to resolve capabilities, using defaults.";
+ m_maxBlurSamples = QT5COMPAT_MAX_BLUR_SAMPLES_GL;
+ }
+ } else
+#endif
+ m_maxBlurSamples = QT5COMPAT_MAX_BLUR_SAMPLES;
+}
+
+/*
+
+ The algorithm works like this..
+
+ For every two pixels we want to sample we take one sample between those
+ two pixels and rely on linear interpoliation to get both values at the
+ cost of one texture sample. The sample point is calculated based on the
+ gaussian weights at the two texels.
+
+ I've included the table here for future reference:
+
+ Requested Effective Actual Actual
+ Samples Radius/Kernel Samples Radius(*)
+ -------------------------------------------------
+ 0 0 / 1x1 1 0
+ 1 0 / 1x1 1 0
+ 2 1 / 3x3 2 0
+ 3 1 / 3x3 2 0
+ 4 2 / 5x5 3 1
+ 5 2 / 5x5 3 1
+ 6 3 / 7x7 4 1
+ 7 3 / 7x7 4 1
+ 8 4 / 9x9 5 2
+ 9 4 / 9x9 5 2
+ 10 5 / 11x11 6 2
+ 11 5 / 11x11 6 2
+ 12 6 / 13x13 7 3
+ 13 6 / 13x13 7 3
+ ... ... ... ...
+
+ When ActualSamples is an 'odd' nunber, sample center pixel separately:
+ EffectiveRadius: 4
+ EffectiveKernel: 9x9
+ ActualSamples: 5
+ -4 -3 -2 -1 0 +1 +2 +3 +4
+ | | | | | | | | | |
+ \ / \ / | \ / \ /
+ tL2 tL1 tC tR1 tR2
+
+ When ActualSamples is an 'even' number, sample 3 center pixels with two
+ samples:
+ EffectiveRadius: 3
+ EffectiveKernel: 7x7
+ ActualSamples: 4
+ -3 -2 -1 0 +1 +2 +3
+ | | | | | | | |
+ \ / \ / | \ /
+ tL1 tL0 tR0 tR2
+
+ From this table we have the following formulas:
+ EffectiveRadius = RequestedSamples / 2;
+ EffectiveKernel = EffectiveRadius * 2 + 1
+ ActualSamples = 1 + RequstedSamples / 2;
+ ActualRadius = RequestedSamples / 4;
+
+ (*) ActualRadius excludes the pixel pair sampled in the center
+ for even 'actual sample' counts
+*/
+
+static qreal qgfx_gaussian(qreal x, qreal d)
+{
+ return qExp(- x * x / (2 * d * d));
+}
+
+struct QGfxGaussSample
+{
+ QByteArray name;
+ qreal pos;
+ qreal weight;
+ inline void set(const QByteArray &n, qreal p, qreal w) {
+ name = n;
+ pos = p;
+ weight = w;
+ }
+};
+
+static void qgfx_declareBlur(QByteArray &shader, const QByteArray& direction, QGfxGaussSample *s, int samples)
+{
+ for (int i=0; i<samples; ++i) {
+ shader += "layout(location = " + QByteArray::number(i) + ") " + direction + " vec2 ";
+ shader += s[i].name;
+ shader += ";\n";
+ }
+}
+
+static void qgfx_buildGaussSamplePoints(QGfxGaussSample *p, int samples, int radius, qreal deviation)
+{
+
+ if ((samples % 2) == 1) {
+ p[radius].set("tC", 0, 1);
+ for (int i=0; i<radius; ++i) {
+ qreal p0 = (i + 1) * 2 - 1;
+ qreal p1 = (i + 1) * 2;
+ qreal w0 = qgfx_gaussian(p0, deviation);
+ qreal w1 = qgfx_gaussian(p1, deviation);
+ qreal w = w0 + w1;
+ qreal samplePos = (p0 * w0 + p1 * w1) / w;
+ if (qIsNaN(samplePos)) {
+ samplePos = 0;
+ w = 0;
+ }
+ p[radius - i - 1].set("tL" + QByteArray::number(i), samplePos, w);
+ p[radius + i + 1].set("tR" + QByteArray::number(i), -samplePos, w);
+ }
+ } else {
+ { // tL0
+ qreal wl = qgfx_gaussian(-1.0, deviation);
+ qreal wc = qgfx_gaussian(0.0, deviation);
+ qreal w = wl + wc;
+ p[radius].set("tL0", -1.0 * wl / w, w);
+ p[radius+1].set("tR0", 1.0, wl); // reuse wl as gauss(-1)==gauss(1);
+ }
+ for (int i=0; i<radius; ++i) {
+ qreal p0 = (i + 1) * 2;
+ qreal p1 = (i + 1) * 2 + 1;
+ qreal w0 = qgfx_gaussian(p0, deviation);
+ qreal w1 = qgfx_gaussian(p1, deviation);
+ qreal w = w0 + w1;
+ qreal samplePos = (p0 * w0 + p1 * w1) / w;
+ if (qIsNaN(samplePos)) {
+ samplePos = 0;
+ w = 0;
+ }
+ p[radius - i - 1].set("tL" + QByteArray::number(i+1), samplePos, w);
+ p[radius + i + 2].set("tR" + QByteArray::number(i+1), -samplePos, w);
+
+ }
+ }
+}
+
+void qgfx_declareUniforms(QByteArray &shader, bool alphaOnly)
+{
+ shader += "layout(std140, binding = 0) uniform buf {\n"
+ " mat4 qt_Matrix;\n"
+ " float qt_Opacity;\n"
+ " float spread;\n"
+ " vec2 dirstep;\n";
+
+ if (alphaOnly) {
+ shader += " vec4 color;\n"
+ " float thickness;\n";
+ }
+ shader += "};\n\n";
+}
+
+QByteArray qgfx_gaussianVertexShader(QGfxGaussSample *p, int samples, bool alphaOnly)
+{
+ QByteArray shader;
+ shader.reserve(1024);
+ shader += "#version 440\n\n"
+ "layout(location = 0) in vec4 qt_Vertex;\n"
+ "layout(location = 1) in vec2 qt_MultiTexCoord0;\n\n";
+
+ qgfx_declareUniforms(shader, alphaOnly);
+
+ shader += "out gl_PerVertex { vec4 gl_Position; };\n\n";
+
+ qgfx_declareBlur(shader, "out", p, samples);
+
+ shader += "\nvoid main() {\n"
+ " gl_Position = qt_Matrix * qt_Vertex;\n\n";
+
+ for (int i=0; i<samples; ++i) {
+ shader += " ";
+ shader += p[i].name;
+ shader += " = qt_MultiTexCoord0";
+ if (p[i].pos != 0.0) {
+ shader += " + spread * dirstep * float(";
+ shader += QByteArray::number(p[i].pos);
+ shader += ')';
+ }
+ shader += ";\n";
+ }
+
+ shader += "}\n";
+
+ return shader;
+}
+
+QByteArray qgfx_gaussianFragmentShader(QGfxGaussSample *p, int samples, bool alphaOnly)
+{
+ QByteArray shader;
+ shader.reserve(1024);
+ shader += "#version 440\n\n";
+
+ qgfx_declareUniforms(shader, alphaOnly);
+
+ shader += "layout(binding = 1) uniform sampler2D source;";
+ shader += "layout(location = 0) out vec4 fragColor;\n";
+
+ qgfx_declareBlur(shader, "in", p, samples);
+
+ shader += "\nvoid main() {\n"
+ " fragColor = ";
+ if (alphaOnly)
+ shader += "mix(vec4(0), color, clamp((";
+ else
+ shader += "(";
+
+ qreal sum = 0;
+ for (int i=0; i<samples; ++i)
+ sum += p[i].weight;
+
+ for (int i=0; i<samples; ++i) {
+ shader += "\n + float(";
+ shader += QByteArray::number(p[i].weight / sum);
+ shader += ") * texture(source, ";
+ shader += p[i].name;
+ shader += ")";
+ if (alphaOnly)
+ shader += ".a";
+ }
+
+ shader += "\n )";
+ if (alphaOnly)
+ shader += "/thickness, 0.0, 1.0))";
+ shader += "* qt_Opacity;\n}";
+
+ return shader;
+}
+
+static QByteArray qgfx_fallbackVertexShader(bool alphaOnly)
+{
+ QByteArray vertexShader =
+ "#version 440\n"
+ "layout(location = 0) in vec4 qt_Vertex;\n"
+ "layout(location = 1) in vec2 qt_MultiTexCoord0;\n\n";
+
+ qgfx_declareUniforms(vertexShader, alphaOnly);
+
+ vertexShader +=
+ "layout(location = 0) out vec2 qt_TexCoord0;\n"
+ "out gl_PerVertex { vec4 gl_Position; };\n"
+ "void main() {\n"
+ " gl_Position = qt_Matrix * qt_Vertex;\n"
+ " qt_TexCoord0 = qt_MultiTexCoord0;\n"
+ "}\n";
+
+ return vertexShader;
+}
+
+static QByteArray qgfx_fallbackFragmentShader(int requestedRadius, qreal deviation, bool masked, bool alphaOnly)
+{
+ QByteArray fragShader = "#version 440\n\n";
+
+ qgfx_declareUniforms(fragShader, alphaOnly);
+
+ fragShader += "layout(binding = 1) uniform sampler2D source;\n";
+ if (masked)
+ fragShader += "layout(binding = 2) uniform sampler2D mask;\n";
+
+ fragShader +=
+ "layout(location = 0) out vec4 fragColor;\n"
+ "layout(location = 0) in vec2 qt_TexCoord0;\n"
+ "\n"
+ "void main() {\n";
+ if (alphaOnly)
+ fragShader += " float result = 0.0;\n";
+ else
+ fragShader += " vec4 result = vec4(0);\n";
+ fragShader += " vec2 pixelStep = dirstep * spread;\n";
+ if (masked)
+ fragShader += " pixelStep *= texture(mask, qt_TexCoord0).a;\n";
+
+ float wSum = 0;
+ for (int r=-requestedRadius; r<=requestedRadius; ++r) {
+ float w = qgfx_gaussian(r, deviation);
+ wSum += w;
+ fragShader += " result += float(";
+ fragShader += QByteArray::number(w);
+ fragShader += ") * texture(source, qt_TexCoord0 + pixelStep * float(";
+ fragShader += QByteArray::number(r);
+ fragShader += "))";
+ if (alphaOnly)
+ fragShader += ".a";
+ fragShader += ";\n";
+ }
+ fragShader += " const float wSum = float(";
+ fragShader += QByteArray::number(wSum);
+ fragShader += ");\n"
+ " fragColor = ";
+ if (alphaOnly)
+ fragShader += "mix(vec4(0), color, clamp((result / wSum) / thickness, 0.0, 1.0)) * qt_Opacity;\n";
+ else
+ fragShader += "(qt_Opacity / wSum) * result;\n";
+ fragShader += "}\n";
+
+ return fragShader;
+}
+
+QVariantMap QGfxShaderBuilder::gaussianBlur(const QJSValue &parameters)
+{
+ int requestedRadius = qMax(0.0, parameters.property(QStringLiteral("radius")).toNumber());
+ qreal deviation = parameters.property(QStringLiteral("deviation")).toNumber();
+ bool masked = parameters.property(QStringLiteral("masked")).toBool();
+ bool alphaOnly = parameters.property(QStringLiteral("alphaOnly")).toBool();
+
+ int requestedSamples = requestedRadius * 2 + 1;
+ int samples = 1 + requestedSamples / 2;
+ int radius = requestedSamples / 4;
+ bool fallback = parameters.property(QStringLiteral("fallback")).toBool();
+
+ QVariantMap result;
+
+ QByteArray vertexShader;
+ QByteArray fragmentShader;
+ if (samples > m_maxBlurSamples || masked || fallback) {
+ fragmentShader = qgfx_fallbackFragmentShader(requestedRadius, deviation, masked, alphaOnly);
+ vertexShader = qgfx_fallbackVertexShader(alphaOnly);
+ } else {
+ QVarLengthArray<QGfxGaussSample, 64> p(samples);
+ qgfx_buildGaussSamplePoints(p.data(), samples, radius, deviation);
+
+ fragmentShader = qgfx_gaussianFragmentShader(p.data(), samples, alphaOnly);
+ vertexShader = qgfx_gaussianVertexShader(p.data(), samples, alphaOnly);
+ }
+
+ result["fragmentShader"] = buildFragmentShader(fragmentShader);
+ result["vertexShader"] = buildVertexShader(vertexShader);
+ return result;
+}
+
+QUrl QGfxShaderBuilder::buildFragmentShader(const QByteArray &code)
+{
+ delete m_fragmentShader;
+ m_fragmentShader = new QTemporaryFile(this);
+
+ return buildShader(code, QShader::FragmentStage, m_fragmentShader);
+}
+
+QUrl QGfxShaderBuilder::buildVertexShader(const QByteArray &code)
+{
+ delete m_vertexShader;
+ m_vertexShader = new QTemporaryFile(this);
+
+ return buildShader(code, QShader::VertexStage, m_vertexShader);
+}
+
+QUrl QGfxShaderBuilder::buildShader(const QByteArray &code,
+ QShader::Stage stage,
+ QTemporaryFile *output)
+{
+ if (!output->open()) {
+ qWarning() << "QGfxShaderBuilder: Failed to create temporary files";
+ return QUrl{};
+ }
+
+ m_shaderBaker.setSourceString(code, stage, output->fileName());
+ {
+ QShader compiledShader = m_shaderBaker.bake();
+ if (!compiledShader.isValid()) {
+ qWarning() << "QGfxShaderBuilder: Failed to compile shader for stage "
+ << stage << ": "
+ << m_shaderBaker.errorMessage()
+ << QString(code).replace('\n', QChar(QChar::LineFeed));
+ return QUrl{};
+ }
+ output->write(compiledShader.serialized());
+ }
+
+ output->close();
+
+ return QUrl::fromLocalFile(output->fileName());
+}
+
diff --git a/src/imports/graphicaleffects5/private/qgfxshaderbuilder_p.h b/src/imports/graphicaleffects5/private/qgfxshaderbuilder_p.h
new file mode 100644
index 0000000..5e80ce3
--- /dev/null
+++ b/src/imports/graphicaleffects5/private/qgfxshaderbuilder_p.h
@@ -0,0 +1,77 @@
+/****************************************************************************
+**
+** Copyright (C) 2016 Jolla Ltd, author: <gunnar.sletta@jollamobile.com>
+** Contact: http://www.qt-project.org/legal
+**
+** This file is part of the Qt Graphical Effects module of the Qt Toolkit.
+**
+** $QT_BEGIN_LICENSE:LGPL$
+** Commercial License Usage
+** Licensees holding valid commercial Qt licenses may use this file in
+** accordance with the commercial license agreement provided with the
+** Software or, alternatively, in accordance with the terms contained in
+** a written agreement between you and The Qt Company. For licensing terms
+** and conditions see https://www.qt.io/terms-conditions. For further
+** information use the contact form at https://www.qt.io/contact-us.
+**
+** GNU Lesser General Public License Usage
+** Alternatively, this file may be used under the terms of the GNU Lesser
+** General Public License version 3 as published by the Free Software
+** Foundation and appearing in the file LICENSE.LGPL3 included in the
+** packaging of this file. Please review the following information to
+** ensure the GNU Lesser General Public License version 3 requirements
+** will be met: https://www.gnu.org/licenses/lgpl-3.0.html.
+**
+** GNU General Public License Usage
+** Alternatively, this file may be used under the terms of the GNU
+** General Public License version 2.0 or (at your option) the GNU General
+** Public license version 3 or any later version approved by the KDE Free
+** Qt Foundation. The licenses are as published by the Free Software
+** Foundation and appearing in the file LICENSE.GPL2 and LICENSE.GPL3
+** included in the packaging of this file. Please review the following
+** information to ensure the GNU General Public License requirements will
+** be met: https://www.gnu.org/licenses/gpl-2.0.html and
+** https://www.gnu.org/licenses/gpl-3.0.html.
+**
+** $QT_END_LICENSE$
+**
+****************************************************************************/
+
+#ifndef QGFXSHADERBUILDER_P_H
+#define QGFXSHADERBUILDER_P_H
+
+#include <QtCore/QObject>
+#include <QtCore/QVariantMap>
+#include <QtCore/QUrl>
+#include <QtShaderTools/private/qshaderbaker_p.h>
+#include <QtGui/private/qshader_p.h>
+
+#include <QtQml/QJSValue>
+
+QT_BEGIN_NAMESPACE
+
+class QTemporaryFile;
+class QGfxShaderBuilder : public QObject
+{
+ Q_OBJECT
+
+public:
+ QGfxShaderBuilder();
+
+ Q_INVOKABLE QVariantMap gaussianBlur(const QJSValue &parameters);
+ Q_INVOKABLE QUrl buildVertexShader(const QByteArray &code);
+ Q_INVOKABLE QUrl buildFragmentShader(const QByteArray &code);
+
+private:
+ QUrl buildShader(const QByteArray &code, QShader::Stage stage, QTemporaryFile *output);
+
+ int m_maxBlurSamples = 0;
+ QShaderBaker m_shaderBaker;
+
+ QTemporaryFile *m_fragmentShader = nullptr;
+ QTemporaryFile *m_vertexShader = nullptr;
+};
+
+QT_END_NAMESPACE
+
+#endif // QGFXSHADERBUILDER_P_H
diff --git a/src/imports/graphicaleffects5/private/qgfxsourceproxy.cpp b/src/imports/graphicaleffects5/private/qgfxsourceproxy.cpp
index cf64807..1ec8ae4 100644
--- a/src/imports/graphicaleffects5/private/qgfxsourceproxy.cpp
+++ b/src/imports/graphicaleffects5/private/qgfxsourceproxy.cpp
@@ -1,11 +1,11 @@
/****************************************************************************
**
** Copyright (C) 2016 Jolla Ltd, author: <gunnar.sletta@jollamobile.com>
-** Contact: https://www.qt.io/licensing/
+** Contact: http://www.qt-project.org/legal
**
** This file is part of the Qt Graphical Effects module of the Qt Toolkit.
**
-** $QT_BEGIN_LICENSE:BSD$
+** $QT_BEGIN_LICENSE:LGPL$
** Commercial License Usage
** Licensees holding valid commercial Qt licenses may use this file in
** accordance with the commercial license agreement provided with the
@@ -14,35 +14,24 @@
** and conditions see https://www.qt.io/terms-conditions. For further
** information use the contact form at https://www.qt.io/contact-us.
**
-** BSD License Usage
-** Alternatively, you may use this file under the terms of the BSD license
-** as follows:
+** GNU Lesser General Public License Usage
+** Alternatively, this file may be used under the terms of the GNU Lesser
+** General Public License version 3 as published by the Free Software
+** Foundation and appearing in the file LICENSE.LGPL3 included in the
+** packaging of this file. Please review the following information to
+** ensure the GNU Lesser General Public License version 3 requirements
+** will be met: https://www.gnu.org/licenses/lgpl-3.0.html.
**
-** "Redistribution and use in source and binary forms, with or without
-** modification, are permitted provided that the following conditions are
-** met:
-** * Redistributions of source code must retain the above copyright
-** notice, this list of conditions and the following disclaimer.
-** * Redistributions in binary form must reproduce the above copyright
-** notice, this list of conditions and the following disclaimer in
-** the documentation and/or other materials provided with the
-** distribution.
-** * Neither the name of The Qt Company Ltd nor the names of its
-** contributors may be used to endorse or promote products derived
-** from this software without specific prior written permission.
-**
-**
-** THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
-** "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
-** LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
-** A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
-** OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
-** SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
-** LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
-** DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
-** THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
-** (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
-** OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE."
+** GNU General Public License Usage
+** Alternatively, this file may be used under the terms of the GNU
+** General Public License version 2.0 or (at your option) the GNU General
+** Public license version 3 or any later version approved by the KDE Free
+** Qt Foundation. The licenses are as published by the Free Software
+** Foundation and appearing in the file LICENSE.GPL2 and LICENSE.GPL3
+** included in the packaging of this file. Please review the following
+** information to ensure the GNU General Public License requirements will
+** be met: https://www.gnu.org/licenses/gpl-2.0.html and
+** https://www.gnu.org/licenses/gpl-3.0.html.
**
** $QT_END_LICENSE$
**
diff --git a/src/imports/graphicaleffects5/private/qgfxsourceproxy_p.h b/src/imports/graphicaleffects5/private/qgfxsourceproxy_p.h
index 8fe592c..3d57b08 100644
--- a/src/imports/graphicaleffects5/private/qgfxsourceproxy_p.h
+++ b/src/imports/graphicaleffects5/private/qgfxsourceproxy_p.h
@@ -1,11 +1,11 @@
/****************************************************************************
**
** Copyright (C) 2016 Jolla Ltd, author: <gunnar.sletta@jollamobile.com>
-** Contact: https://www.qt.io/licensing/
+** Contact: http://www.qt-project.org/legal
**
** This file is part of the Qt Graphical Effects module of the Qt Toolkit.
**
-** $QT_BEGIN_LICENSE:BSD$
+** $QT_BEGIN_LICENSE:LGPL$
** Commercial License Usage
** Licensees holding valid commercial Qt licenses may use this file in
** accordance with the commercial license agreement provided with the
@@ -14,35 +14,24 @@
** and conditions see https://www.qt.io/terms-conditions. For further
** information use the contact form at https://www.qt.io/contact-us.
**
-** BSD License Usage
-** Alternatively, you may use this file under the terms of the BSD license
-** as follows:
+** GNU Lesser General Public License Usage
+** Alternatively, this file may be used under the terms of the GNU Lesser
+** General Public License version 3 as published by the Free Software
+** Foundation and appearing in the file LICENSE.LGPL3 included in the
+** packaging of this file. Please review the following information to
+** ensure the GNU Lesser General Public License version 3 requirements
+** will be met: https://www.gnu.org/licenses/lgpl-3.0.html.
**
-** "Redistribution and use in source and binary forms, with or without
-** modification, are permitted provided that the following conditions are
-** met:
-** * Redistributions of source code must retain the above copyright
-** notice, this list of conditions and the following disclaimer.
-** * Redistributions in binary form must reproduce the above copyright
-** notice, this list of conditions and the following disclaimer in
-** the documentation and/or other materials provided with the
-** distribution.
-** * Neither the name of The Qt Company Ltd nor the names of its
-** contributors may be used to endorse or promote products derived
-** from this software without specific prior written permission.
-**
-**
-** THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
-** "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
-** LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
-** A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
-** OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
-** SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
-** LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
-** DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
-** THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
-** (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
-** OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE."
+** GNU General Public License Usage
+** Alternatively, this file may be used under the terms of the GNU
+** General Public License version 2.0 or (at your option) the GNU General
+** Public license version 3 or any later version approved by the KDE Free
+** Qt Foundation. The licenses are as published by the Free Software
+** Foundation and appearing in the file LICENSE.GPL2 and LICENSE.GPL3
+** included in the packaging of this file. Please review the following
+** information to ensure the GNU General Public License requirements will
+** be met: https://www.gnu.org/licenses/gpl-2.0.html and
+** https://www.gnu.org/licenses/gpl-3.0.html.
**
** $QT_END_LICENSE$
**
diff --git a/src/imports/graphicaleffects5/shaders_ng/compile.bat b/src/imports/graphicaleffects5/shaders_ng/compile.bat
index 9eafc03..6f40266 100644
--- a/src/imports/graphicaleffects5/shaders_ng/compile.bat
+++ b/src/imports/graphicaleffects5/shaders_ng/compile.bat
@@ -56,6 +56,8 @@ qsb --glsl "150,120,100 es" --hlsl 50 -c --msl 12 -o opacitymask_invert.frag.qsb
qsb --glsl "150,120,100 es" --hlsl 50 -c --msl 12 -o fastblur.frag.qsb fastblur.frag
qsb -b --glsl "150,120,100 es" --hlsl 50 -c --msl 12 -o fastblur_internal.vert.qsb fastblur_internal.vert
qsb --glsl "150,120,100 es" --hlsl 50 -c --msl 12 -o fastblur_internal.frag.qsb fastblur_internal.frag
+qsb --glsl "150,120,100 es" --hlsl 50 -c --msl 12 -o fastinnershadow.frag.qsb fastinnershadow.frag
+qsb --glsl "150,120,100 es" --hlsl 50 -c --msl 12 -o fastinnershadow_level0.frag.qsb fastinnershadow_level0.frag
qsb --glsl "150,120,100 es" --hlsl 50 -c --msl 12 -o fastglow.frag.qsb fastglow.frag
qsb --glsl "150,120,100 es" --hlsl 50 -c --msl 12 -o colorize.frag.qsb colorize.frag
qsb --glsl "150,120,100 es" --hlsl 50 -c --msl 12 -o brightnesscontrast.frag.qsb brightnesscontrast.frag
@@ -63,6 +65,8 @@ qsb --glsl "150,120,100 es" --hlsl 50 -c --msl 12 -o coloroverlay.frag.qsb color
qsb --glsl "150,120,100 es" --hlsl 50 -c --msl 12 -o desaturate.frag.qsb desaturate.frag
qsb --glsl "150,120,100 es" --hlsl 50 -c --msl 12 -o displace.frag.qsb displace.frag
qsb --glsl "150,120,100 es" --hlsl 50 -c --msl 12 -o gammaadjust.frag.qsb gammaadjust.frag
+qsb --glsl "150,120,100 es" --hlsl 50 -c --msl 12 -o gaussianinnershadow.frag.qsb gaussianinnershadow.frag
+qsb --glsl "150,120,100 es" --hlsl 50 -c --msl 12 -o gaussianinnershadow_shadow.frag.qsb gaussianinnershadow_shadow.frag
qsb --glsl "150,120,100 es" --hlsl 50 -c --msl 12 -o huesaturation.frag.qsb huesaturation.frag
qsb --glsl "150,120,100 es" --hlsl 50 -c --msl 12 -o rectangularglow.frag.qsb rectangularglow.frag
qsb --glsl "150,120,100 es" --hlsl 50 -c --msl 12 -o thresholdmask.frag.qsb thresholdmask.frag
@@ -72,6 +76,8 @@ qsb --glsl "150,120,100 es" --hlsl 50 -c --msl 12 -o lineargradient_mask.frag.qs
qsb -b --glsl "150,120,100 es" --hlsl 50 -c --msl 12 -o radialgradient.vert.qsb radialgradient.vert
qsb --glsl "150,120,100 es" --hlsl 50 -c --msl 12 -o radialgradient_nomask.frag.qsb radialgradient_nomask.frag
qsb --glsl "150,120,100 es" --hlsl 50 -c --msl 12 -o radialgradient_mask.frag.qsb radialgradient_mask.frag
+qsb --glsl "150,120,100 es" --hlsl 50 -c --msl 12 -o recursiveblur.frag.qsb recursiveblur.frag
+qsb -b --glsl "150,120,100 es" --hlsl 50 -c --msl 12 -o recursiveblur.vert.qsb recursiveblur.vert
qsb --glsl "150,120,100 es" --hlsl 50 -c --msl 12 -o conicalgradient_nomask.frag.qsb conicalgradient_nomask.frag
qsb --glsl "150,120,100 es" --hlsl 50 -c --msl 12 -o conicalgradient_mask.frag.qsb conicalgradient_mask.frag
qsb --glsl "150,120,100 es" --hlsl 50 -c --msl 12 -o leveladjust.frag.qsb leveladjust.frag
diff --git a/src/imports/graphicaleffects5/shaders_ng/fastinnershadow.frag b/src/imports/graphicaleffects5/shaders_ng/fastinnershadow.frag
new file mode 100644
index 0000000..4463286
--- /dev/null
+++ b/src/imports/graphicaleffects5/shaders_ng/fastinnershadow.frag
@@ -0,0 +1,37 @@
+#version 440
+
+layout(location = 0) in vec2 qt_TexCoord0;
+layout(location = 0) out vec4 fragColor;
+
+layout(std140, binding = 0) uniform buf {
+ mat4 qt_Matrix;
+ float qt_Opacity;
+ uniform float weight1;
+ uniform float weight2;
+ uniform float weight3;
+ uniform float weight4;
+ uniform float weight5;
+ uniform vec4 color;
+ uniform float spread;
+};
+layout(binding = 1) uniform sampler2D original;
+layout(binding = 2) uniform sampler2D source1;
+layout(binding = 3) uniform sampler2D source2;
+layout(binding = 4) uniform sampler2D source3;
+layout(binding = 5) uniform sampler2D source4;
+layout(binding = 6) uniform sampler2D source5;
+
+float linearstep(float e0, float e1, float x) {
+ return clamp((x - e0) / (e1 - e0), 0.0, 1.0);
+}
+
+void main() {
+ vec4 shadowColor = texture(source1, qt_TexCoord0) * weight1;
+ shadowColor += texture(source2, qt_TexCoord0) * weight2;
+ shadowColor += texture(source3, qt_TexCoord0) * weight3;
+ shadowColor += texture(source4, qt_TexCoord0) * weight4;
+ shadowColor += texture(source5, qt_TexCoord0) * weight5;
+ vec4 originalColor = texture(original, qt_TexCoord0);
+ shadowColor.rgb = mix(originalColor.rgb, color.rgb * originalColor.a, linearstep(0.0, spread, shadowColor.a));
+ fragColor = vec4(shadowColor.rgb, originalColor.a) * originalColor.a * qt_Opacity;
+}
diff --git a/src/imports/graphicaleffects5/shaders_ng/fastinnershadow.frag.qsb b/src/imports/graphicaleffects5/shaders_ng/fastinnershadow.frag.qsb
new file mode 100644
index 0000000..e9b5992
--- /dev/null
+++ b/src/imports/graphicaleffects5/shaders_ng/fastinnershadow.frag.qsb
Binary files differ
diff --git a/src/imports/graphicaleffects5/shaders_ng/fastinnershadow_level0.frag b/src/imports/graphicaleffects5/shaders_ng/fastinnershadow_level0.frag
new file mode 100644
index 0000000..e64da56
--- /dev/null
+++ b/src/imports/graphicaleffects5/shaders_ng/fastinnershadow_level0.frag
@@ -0,0 +1,20 @@
+#version 440
+
+layout(location = 0) in vec2 qt_TexCoord0;
+layout(location = 0) out vec4 fragColor;
+
+layout(std140, binding = 0) uniform buf {
+ mat4 qt_Matrix;
+ float qt_Opacity;
+ vec4 color;
+ float horizontalOffset;
+ float verticalOffset;
+};
+layout(binding = 1) uniform sampler2D source;
+
+void main() {
+ vec2 pos = qt_TexCoord0 - vec2(horizontalOffset, verticalOffset);
+ float ea = step(0.0, pos.x) * step(0.0, pos.y) * step(pos.x, 1.0) * step(pos.y, 1.0);
+ float eb = 1.0 - ea;
+ fragColor = (eb * color + ea * color * (1.0 - texture(source, pos).a)) * qt_Opacity;
+}
diff --git a/src/imports/graphicaleffects5/shaders_ng/fastinnershadow_level0.frag.qsb b/src/imports/graphicaleffects5/shaders_ng/fastinnershadow_level0.frag.qsb
new file mode 100644
index 0000000..4ab0691
--- /dev/null
+++ b/src/imports/graphicaleffects5/shaders_ng/fastinnershadow_level0.frag.qsb
Binary files differ
diff --git a/src/imports/graphicaleffects5/shaders_ng/gaussianinnershadow.frag b/src/imports/graphicaleffects5/shaders_ng/gaussianinnershadow.frag
new file mode 100644
index 0000000..476e786
--- /dev/null
+++ b/src/imports/graphicaleffects5/shaders_ng/gaussianinnershadow.frag
@@ -0,0 +1,25 @@
+#version 440
+
+layout(location = 0) in vec2 qt_TexCoord0;
+layout(location = 0) out vec4 fragColor;
+
+layout(std140, binding = 0) uniform buf {
+ mat4 qt_Matrix;
+ float qt_Opacity;
+ float spread;
+ vec4 color;
+};
+
+layout(binding = 1) uniform sampler2D original;
+layout(binding = 2) uniform sampler2D shadow;
+
+float linearstep(float e0, float e1, float x) {
+ return clamp((x - e0) / (e1 - e0), 0.0, 1.0);
+}
+
+void main(void) {
+ vec4 originalColor = texture(original, qt_TexCoord0);
+ vec4 shadowColor = texture(shadow, qt_TexCoord0);
+ shadowColor.rgb = mix(originalColor.rgb, color.rgb * originalColor.a, linearstep(0.0, spread, shadowColor.a));
+ fragColor = vec4(shadowColor.rgb, originalColor.a) * originalColor.a * qt_Opacity;
+}
diff --git a/src/imports/graphicaleffects5/shaders_ng/gaussianinnershadow.frag.qsb b/src/imports/graphicaleffects5/shaders_ng/gaussianinnershadow.frag.qsb
new file mode 100644
index 0000000..50a9cb9
--- /dev/null
+++ b/src/imports/graphicaleffects5/shaders_ng/gaussianinnershadow.frag.qsb
Binary files differ
diff --git a/src/imports/graphicaleffects5/shaders_ng/gaussianinnershadow_shadow.frag b/src/imports/graphicaleffects5/shaders_ng/gaussianinnershadow_shadow.frag
new file mode 100644
index 0000000..b8d8892
--- /dev/null
+++ b/src/imports/graphicaleffects5/shaders_ng/gaussianinnershadow_shadow.frag
@@ -0,0 +1,20 @@
+#version 440
+
+layout(location = 0) in vec2 qt_TexCoord0;
+layout(location = 0) out vec4 fragColor;
+
+layout(std140, binding = 0) uniform buf {
+ mat4 qt_Matrix;
+ float qt_Opacity;
+ vec4 color;
+ float horizontalOffset;
+ float verticalOffset;
+};
+layout(binding = 1) uniform sampler2D original;
+
+void main(void) {
+ vec2 pos = qt_TexCoord0 - vec2(horizontalOffset, verticalOffset);
+ float ea = step(0.0, pos.x) * step(0.0, pos.y) * step(pos.x, 1.0) * step(pos.y, 1.0);
+ float eb = 1.0 - ea;
+ fragColor = eb * color + ea * color * (1.0 - texture(original, pos).a) * qt_Opacity;
+}
diff --git a/src/imports/graphicaleffects5/shaders_ng/gaussianinnershadow_shadow.frag.qsb b/src/imports/graphicaleffects5/shaders_ng/gaussianinnershadow_shadow.frag.qsb
new file mode 100644
index 0000000..1b8a93f
--- /dev/null
+++ b/src/imports/graphicaleffects5/shaders_ng/gaussianinnershadow_shadow.frag.qsb
Binary files differ
diff --git a/src/imports/graphicaleffects5/shaders_ng/recursiveblur.frag b/src/imports/graphicaleffects5/shaders_ng/recursiveblur.frag
new file mode 100644
index 0000000..5b47660
--- /dev/null
+++ b/src/imports/graphicaleffects5/shaders_ng/recursiveblur.frag
@@ -0,0 +1,16 @@
+#version 440
+
+layout(location = 0) in vec2 qt_TexCoord0;
+layout(location = 0) out vec4 fragColor;
+
+layout(std140, binding = 0) uniform buf {
+ mat4 qt_Matrix;
+ float qt_Opacity;
+ float expandX;
+ float expandY;
+};
+layout(binding = 1) uniform sampler2D source;
+
+void main() {
+ fragColor = texture(source, qt_TexCoord0) * qt_Opacity;
+}
diff --git a/src/imports/graphicaleffects5/shaders_ng/recursiveblur.frag.qsb b/src/imports/graphicaleffects5/shaders_ng/recursiveblur.frag.qsb
new file mode 100644
index 0000000..ff46026
--- /dev/null
+++ b/src/imports/graphicaleffects5/shaders_ng/recursiveblur.frag.qsb
Binary files differ
diff --git a/src/imports/graphicaleffects5/shaders_ng/recursiveblur.vert b/src/imports/graphicaleffects5/shaders_ng/recursiveblur.vert
new file mode 100644
index 0000000..050825d
--- /dev/null
+++ b/src/imports/graphicaleffects5/shaders_ng/recursiveblur.vert
@@ -0,0 +1,22 @@
+#version 440
+
+layout(location = 0) in vec4 qt_Vertex;
+layout(location = 1) in vec2 qt_MultiTexCoord0;
+layout(location = 0) out vec2 qt_TexCoord0;
+
+layout(std140, binding = 0) uniform buf {
+ mat4 qt_Matrix;
+ float qt_Opacity;
+ float expandX;
+ float expandY;
+};
+
+out gl_PerVertex { vec4 gl_Position; };
+
+void main() {
+ vec2 texCoord = qt_MultiTexCoord0;
+ texCoord.s = (texCoord.s - expandX) / (1.0 - 2.0 * expandX);
+ texCoord.t = (texCoord.t - expandY) / (1.0 - 2.0 * expandY);
+ qt_TexCoord0 = texCoord;
+ gl_Position = qt_Matrix * qt_Vertex;
+}
diff --git a/src/imports/graphicaleffects5/shaders_ng/recursiveblur.vert.qsb b/src/imports/graphicaleffects5/shaders_ng/recursiveblur.vert.qsb
new file mode 100644
index 0000000..b1b75d8
--- /dev/null
+++ b/src/imports/graphicaleffects5/shaders_ng/recursiveblur.vert.qsb
Binary files differ