diff --git a/extension.js b/extension.js
index 207a8ce..ae4452e 100644
--- a/extension.js
+++ b/extension.js
@@ -58,6 +58,7 @@ class Extension {
new Me.imports.src.Hexagon.Hexagon(),
new Me.imports.src.Incinerate.Incinerate(),
new Me.imports.src.Matrix.Matrix(),
+ new Me.imports.src.Pixelate.Pixelate(),
new Me.imports.src.SnapOfDisintegration.SnapOfDisintegration(),
new Me.imports.src.TRexAttack.TRexAttack(),
new Me.imports.src.TVEffect.TVEffect(),
diff --git a/kwin/build.sh b/kwin/build.sh
index 2bbf5bc..fd6e2f3 100755
--- a/kwin/build.sh
+++ b/kwin/build.sh
@@ -133,6 +133,7 @@ generate "energize-b" "Energize B [Burn-My-Windows]" "Using different transporte
generate "fire" "Fire [Burn-My-Windows]" "The classic effect inspired by Compiz"
generate "hexagon" "Hexagon [Burn-My-Windows]" "With glowing lines and hexagon-shaped tiles, this effect looks very sci-fi"
generate "incinerate" "Incinerate [Burn-My-Windows]" "A less snappy but definitely more fancy take on the fire effect"
+generate "pixelate" "Pixelate [Burn-My-Windows]" "Pixelate the window and randomly hide the pixels"
generate "tv" "TV Effect [Burn-My-Windows]" "Make windows close like turning off a TV"
generate "wisps" "Wisps [Burn-My-Windows]" "Let your windows be carried away to the realm of dreams by these little fairies"
diff --git a/kwin/pixelate/config.ui b/kwin/pixelate/config.ui
new file mode 100755
index 0000000..3fa647c
--- /dev/null
+++ b/kwin/pixelate/config.ui
@@ -0,0 +1,132 @@
+
+
+ BMWConfigForm
+
+
+
+ 0
+ 0
+ 562
+ 365
+
+
+
+ -
+
+
+ Line Color:
+
+
+ Qt::AlignRight|Qt::AlignTrailing|Qt::AlignVCenter
+
+
+
+ -
+
+
+ 1.000000000000000
+
+
+ 5.000000000000000
+
+
+
+ -
+
+
+ 0.100000000000000
+
+
+ 10.000000000000000
+
+
+
+ -
+
+
+ milliseconds
+
+
+ 100
+
+
+ 9999
+
+
+ 100
+
+
+
+ -
+
+
+ Glow Color:
+
+
+ Qt::AlignRight|Qt::AlignTrailing|Qt::AlignVCenter
+
+
+
+ -
+
+
+ Line Width:
+
+
+ Qt::AlignRight|Qt::AlignTrailing|Qt::AlignVCenter
+
+
+
+ -
+
+
+ Duration:
+
+
+ Qt::AlignRight|Qt::AlignTrailing|Qt::AlignVCenter
+
+
+
+ -
+
+
+ Scale:
+
+
+ Qt::AlignRight|Qt::AlignTrailing|Qt::AlignVCenter
+
+
+
+ -
+
+
+ Additive Blending
+
+
+
+ -
+
+
+ true
+
+
+
+ -
+
+
+ true
+
+
+
+
+
+
+
+ KColorButton
+ QPushButton
+
+
+
+
+
+
\ No newline at end of file
diff --git a/kwin/pixelate/main.xml b/kwin/pixelate/main.xml
new file mode 100755
index 0000000..b476ecf
--- /dev/null
+++ b/kwin/pixelate/main.xml
@@ -0,0 +1,16 @@
+
+
+
+
+
+ 1500
+
+
+ 40
+
+
+ 10
+
+
+
\ No newline at end of file
diff --git a/kwin/pixelate/onSettingsChanged.js b/kwin/pixelate/onSettingsChanged.js
new file mode 100644
index 0000000..93aec00
--- /dev/null
+++ b/kwin/pixelate/onSettingsChanged.js
@@ -0,0 +1,6 @@
+// This part is automatically included in the effect's source during the build process.
+// The code below is called whenever the user changes something in the configuration of
+// the effect.
+
+effect.setUniform(this.shader, 'uNoise', effect.readConfig('Noise', 1.0));
+effect.setUniform(this.shader, 'uPixelSize', effect.readConfig('PixelSize', 1.0));
diff --git a/prefs.js b/prefs.js
index 3bc0863..64799c0 100644
--- a/prefs.js
+++ b/prefs.js
@@ -54,6 +54,7 @@ var PreferencesDialog = class PreferencesDialog {
new Me.imports.src.Hexagon.Hexagon(),
new Me.imports.src.Incinerate.Incinerate(),
new Me.imports.src.Matrix.Matrix(),
+ new Me.imports.src.Pixelate.Pixelate(),
new Me.imports.src.SnapOfDisintegration.SnapOfDisintegration(),
new Me.imports.src.TRexAttack.TRexAttack(),
new Me.imports.src.TVEffect.TVEffect(),
diff --git a/resources/shaders/pixelate.frag b/resources/shaders/pixelate.frag
new file mode 100644
index 0000000..12e4557
--- /dev/null
+++ b/resources/shaders/pixelate.frag
@@ -0,0 +1,36 @@
+//////////////////////////////////////////////////////////////////////////////////////////
+// ) ( //
+// ( /( ( ( ) ( ( ( ( )\ ) ( ( //
+// )\()) ))\ )( ( ( )\ ) )\))( )\ ( (()/( ( )\))( ( //
+// ((_)\ /((_|()\ )\ ) )\ '(()/( ((_)()((_) )\ ) ((_)))\((_)()\ )\ //
+// | |(_|_))( ((_)_(_/( _((_)) )(_)) _(()((_|_)_(_/( _| |((_)(()((_|(_) //
+// | '_ \ || | '_| ' \)) | ' \()| || | \ V V / | ' \)) _` / _ \ V V (_-< //
+// |_.__/\_,_|_| |_||_| |_|_|_| \_, | \_/\_/|_|_||_|\__,_\___/\_/\_//__/ //
+// |__/ //
+// Copyright (c) 2021 Simon Schneegans //
+// Released under the GPLv3 or later. See LICENSE file for details. //
+//////////////////////////////////////////////////////////////////////////////////////////
+
+// The content from common.glsl is automatically prepended to each shader effect.
+
+uniform float uNoise;
+uniform float uPixelSize;
+
+void main() {
+ // We simply inverse the progress for opening windows.
+ float progress = uForOpening ? 1.0 - uProgress : uProgress;
+
+ // The current level of pixelation increases with the progress.
+ float pixelSize = ceil(uPixelSize * progress + 1.0);
+ vec2 pixelGrid = vec2(pixelSize) / uSize;
+ vec2 texcoord = iTexCoord.st - mod(iTexCoord.st, pixelGrid) + pixelGrid * 0.5;
+ vec4 oColor = getInputColor(texcoord);
+
+ // Hide selected pixels based on some random noise.
+ float random = simplex2DFractal(texcoord * uNoise * uSize / 1000.0);
+ if (random * 1.5 - 0.25 < progress) {
+ oColor.a = 0.0;
+ }
+
+ setOutputColor(oColor);
+}
\ No newline at end of file
diff --git a/resources/ui/gtk3/Pixelate.ui b/resources/ui/gtk3/Pixelate.ui
new file mode 100644
index 0000000..e1691a1
--- /dev/null
+++ b/resources/ui/gtk3/Pixelate.ui
@@ -0,0 +1,192 @@
+
+
+
+
+
+
+
+
+
+
+
+
\ No newline at end of file
diff --git a/resources/ui/gtk4/Pixelate.ui b/resources/ui/gtk4/Pixelate.ui
new file mode 100644
index 0000000..9098f61
--- /dev/null
+++ b/resources/ui/gtk4/Pixelate.ui
@@ -0,0 +1,163 @@
+
+
+
+
+ vertical
+
+
+
+
+
+ none
+ 1
+
+
+
+
+ 0
+
+
+
+
+ Animation Time [ms]
+ 0
+ start
+ center
+ 1
+
+
+
+
+ end
+ center
+ 1
+ 0
+ left
+ 300
+
+
+ 10000
+ 100
+ 1
+ 100
+
+
+
+
+
+
+ edit-clear-symbolic
+ Reset to Default Value
+
+
+
+
+
+
+
+
+
+
+ 0
+
+
+
+
+ Randomness
+ 0
+ start
+ center
+ 1
+
+
+
+
+ end
+ center
+ 1
+ 0
+ left
+ 300
+
+
+ 100
+ 1
+ 1
+ 10
+
+
+
+
+
+
+ edit-clear-symbolic
+ Reset to Default Value
+
+
+
+
+
+
+
+
+
+
+ 0
+
+
+
+
+ Pixel Size
+ 0
+ start
+ center
+ 1
+
+
+
+
+ end
+ center
+ 1
+ 0
+ left
+ 300
+
+
+ 50
+ 1
+ 1
+ 10
+
+
+
+
+
+
+ edit-clear-symbolic
+ Reset to Default Value
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
\ No newline at end of file
diff --git a/schemas/org.gnome.shell.extensions.burn-my-windows.gschema.xml b/schemas/org.gnome.shell.extensions.burn-my-windows.gschema.xml
index ee26406..86cc161 100644
--- a/schemas/org.gnome.shell.extensions.burn-my-windows.gschema.xml
+++ b/schemas/org.gnome.shell.extensions.burn-my-windows.gschema.xml
@@ -83,6 +83,41 @@
The amount of suction of the apparition effect.
+
+
+
+
+
+
+ false
+ Pixelate Close Effect
+ Use the Pixelate effect for window closing.
+
+
+
+ false
+ Pixelate Open Effect
+ Use the Pixelate effect for window opening.
+
+
+
+ 500
+ Pixelate Animation Time
+ The time the Pixelate effect takes.
+
+
+
+ 40
+ Pixelate Noise
+ The noise of the effect.
+
+
+
+ 10
+ Pixelate Pixel Size
+ The size of the maximum pixelation.
+
+
diff --git a/src/Pixelate.js b/src/Pixelate.js
new file mode 100644
index 0000000..248f39a
--- /dev/null
+++ b/src/Pixelate.js
@@ -0,0 +1,102 @@
+//////////////////////////////////////////////////////////////////////////////////////////
+// ) ( //
+// ( /( ( ( ) ( ( ( ( )\ ) ( ( //
+// )\()) ))\ )( ( ( )\ ) )\))( )\ ( (()/( ( )\))( ( //
+// ((_)\ /((_|()\ )\ ) )\ '(()/( ((_)()((_) )\ ) ((_)))\((_)()\ )\ //
+// | |(_|_))( ((_)_(_/( _((_)) )(_)) _(()((_|_)_(_/( _| |((_)(()((_|(_) //
+// | '_ \ || | '_| ' \)) | ' \()| || | \ V V / | ' \)) _` / _ \ V V (_-< //
+// |_.__/\_,_|_| |_||_| |_|_|_| \_, | \_/\_/|_|_||_|\__,_\___/\_/\_//__/ //
+// |__/ //
+// Copyright (c) 2021 Simon Schneegans //
+// Released under the GPLv3 or later. See LICENSE file for details. //
+//////////////////////////////////////////////////////////////////////////////////////////
+
+'use strict';
+
+const GObject = imports.gi.GObject;
+
+const _ = imports.gettext.domain('burn-my-windows').gettext;
+
+const ExtensionUtils = imports.misc.extensionUtils;
+const Me = imports.misc.extensionUtils.getCurrentExtension();
+const utils = Me.imports.src.utils;
+const ShaderFactory = Me.imports.src.ShaderFactory.ShaderFactory;
+
+//////////////////////////////////////////////////////////////////////////////////////////
+// This very simple effect pixelates the window texture and randomly hides pixels until //
+// the entire window is gone. //
+//////////////////////////////////////////////////////////////////////////////////////////
+
+// The effect class can be used to get some metadata (like the effect's name or supported
+// GNOME Shell versions), to initialize the respective page of the settings dialog, as
+// well as to create the actual shader for the effect.
+var Pixelate = class {
+
+ // The constructor creates a ShaderFactory which will be used by extension.js to create
+ // shader instances for this effect. The shaders will be automagically created using the
+ // GLSL file in resources/shaders/.glsl. The callback will be called for each
+ // newly created shader instance.
+ constructor() {
+ this.shaderFactory = new ShaderFactory(this.getNick(), (shader) => {
+ // Store uniform locations of newly created shaders.
+ shader._uNoise = shader.get_uniform_location('uNoise');
+ shader._uPixelSize = shader.get_uniform_location('uPixelSize');
+
+ // Write all uniform values at the start of each animation.
+ shader.connect('begin-animation', (shader, settings) => {
+ // clang-format off
+ shader.set_uniform_float(shader._uNoise, 1, [settings.get_double('pixelate-noise')]);
+ shader.set_uniform_float(shader._uPixelSize, 1, [settings.get_double('pixelate-pixel-size')]);
+ // clang-format on
+ });
+ });
+ }
+
+ // ---------------------------------------------------------------------------- metadata
+
+ // The effect is available on all GNOME Shell versions supported by this extension.
+ getMinShellVersion() {
+ return [3, 36];
+ }
+
+ // This will be called in various places where a unique identifier for this effect is
+ // required. It should match the prefix of the settings keys which store whether the
+ // effect is enabled currently (e.g. '*-close-effect'), and its animation time
+ // (e.g. '*-animation-time').
+ getNick() {
+ return 'pixelate';
+ }
+
+ // This will be shown in the sidebar of the preferences dialog as well as in the
+ // drop-down menus where the user can choose the effect.
+ getLabel() {
+ return _('Pixelate');
+ }
+
+ // -------------------------------------------------------------------- API for prefs.js
+
+ // This is called by the preferences dialog. It loads the settings page for this effect,
+ // and binds all properties to the settings.
+ getPreferences(dialog) {
+
+ // Add the settings page to the builder.
+ dialog.getBuilder().add_from_resource(`/ui/${utils.getGTKString()}/Pixelate.ui`);
+
+ // Bind all properties.
+ dialog.bindAdjustment('pixelate-animation-time');
+ dialog.bindAdjustment('pixelate-noise');
+ dialog.bindAdjustment('pixelate-pixel-size');
+
+ // Finally, return the new settings page.
+ return dialog.getBuilder().get_object('pixelate-prefs');
+ }
+
+ // ---------------------------------------------------------------- API for extension.js
+
+ // The getActorScale() is called from extension.js to adjust the actor's size during the
+ // animation. This is useful if the effect requires drawing something beyond the usual
+ // bounds of the actor. This only works for GNOME 3.38+.
+ getActorScale(settings) {
+ return {x: 1.0, y: 1.0};
+ }
+}
diff --git a/tests/generate-references.sh b/tests/generate-references.sh
index 45f26d4..a17f463 100755
--- a/tests/generate-references.sh
+++ b/tests/generate-references.sh
@@ -171,6 +171,7 @@ capture_effect "energize-b"
capture_effect "fire"
capture_effect "hexagon"
capture_effect "incinerate"
+capture_effect "pixelate"
capture_effect "tv"
capture_effect "wisps"
diff --git a/tests/references/pixelate-close-gnome-wayland-nested-32.png b/tests/references/pixelate-close-gnome-wayland-nested-32.png
new file mode 100644
index 0000000..e545ebc
Binary files /dev/null and b/tests/references/pixelate-close-gnome-wayland-nested-32.png differ
diff --git a/tests/references/pixelate-close-gnome-wayland-nested-33.png b/tests/references/pixelate-close-gnome-wayland-nested-33.png
new file mode 100644
index 0000000..1b8becc
Binary files /dev/null and b/tests/references/pixelate-close-gnome-wayland-nested-33.png differ
diff --git a/tests/references/pixelate-close-gnome-wayland-nested-34.png b/tests/references/pixelate-close-gnome-wayland-nested-34.png
new file mode 100644
index 0000000..114dced
Binary files /dev/null and b/tests/references/pixelate-close-gnome-wayland-nested-34.png differ
diff --git a/tests/references/pixelate-close-gnome-wayland-nested-35.png b/tests/references/pixelate-close-gnome-wayland-nested-35.png
new file mode 100644
index 0000000..114dced
Binary files /dev/null and b/tests/references/pixelate-close-gnome-wayland-nested-35.png differ
diff --git a/tests/references/pixelate-close-gnome-wayland-nested-36.png b/tests/references/pixelate-close-gnome-wayland-nested-36.png
new file mode 100644
index 0000000..7644aa2
Binary files /dev/null and b/tests/references/pixelate-close-gnome-wayland-nested-36.png differ
diff --git a/tests/references/pixelate-close-gnome-xsession-32.png b/tests/references/pixelate-close-gnome-xsession-32.png
new file mode 100644
index 0000000..e545ebc
Binary files /dev/null and b/tests/references/pixelate-close-gnome-xsession-32.png differ
diff --git a/tests/references/pixelate-close-gnome-xsession-33.png b/tests/references/pixelate-close-gnome-xsession-33.png
new file mode 100644
index 0000000..1b8becc
Binary files /dev/null and b/tests/references/pixelate-close-gnome-xsession-33.png differ
diff --git a/tests/references/pixelate-close-gnome-xsession-34.png b/tests/references/pixelate-close-gnome-xsession-34.png
new file mode 100644
index 0000000..1eff756
Binary files /dev/null and b/tests/references/pixelate-close-gnome-xsession-34.png differ
diff --git a/tests/references/pixelate-close-gnome-xsession-35.png b/tests/references/pixelate-close-gnome-xsession-35.png
new file mode 100644
index 0000000..1eff756
Binary files /dev/null and b/tests/references/pixelate-close-gnome-xsession-35.png differ
diff --git a/tests/references/pixelate-close-gnome-xsession-36.png b/tests/references/pixelate-close-gnome-xsession-36.png
new file mode 100644
index 0000000..9a8c78f
Binary files /dev/null and b/tests/references/pixelate-close-gnome-xsession-36.png differ
diff --git a/tests/references/pixelate-open-gnome-wayland-nested-32.png b/tests/references/pixelate-open-gnome-wayland-nested-32.png
new file mode 100644
index 0000000..e545ebc
Binary files /dev/null and b/tests/references/pixelate-open-gnome-wayland-nested-32.png differ
diff --git a/tests/references/pixelate-open-gnome-wayland-nested-33.png b/tests/references/pixelate-open-gnome-wayland-nested-33.png
new file mode 100644
index 0000000..1b8becc
Binary files /dev/null and b/tests/references/pixelate-open-gnome-wayland-nested-33.png differ
diff --git a/tests/references/pixelate-open-gnome-wayland-nested-34.png b/tests/references/pixelate-open-gnome-wayland-nested-34.png
new file mode 100644
index 0000000..114dced
Binary files /dev/null and b/tests/references/pixelate-open-gnome-wayland-nested-34.png differ
diff --git a/tests/references/pixelate-open-gnome-wayland-nested-35.png b/tests/references/pixelate-open-gnome-wayland-nested-35.png
new file mode 100644
index 0000000..114dced
Binary files /dev/null and b/tests/references/pixelate-open-gnome-wayland-nested-35.png differ
diff --git a/tests/references/pixelate-open-gnome-wayland-nested-36.png b/tests/references/pixelate-open-gnome-wayland-nested-36.png
new file mode 100644
index 0000000..7644aa2
Binary files /dev/null and b/tests/references/pixelate-open-gnome-wayland-nested-36.png differ
diff --git a/tests/references/pixelate-open-gnome-xsession-32.png b/tests/references/pixelate-open-gnome-xsession-32.png
new file mode 100644
index 0000000..e545ebc
Binary files /dev/null and b/tests/references/pixelate-open-gnome-xsession-32.png differ
diff --git a/tests/references/pixelate-open-gnome-xsession-33.png b/tests/references/pixelate-open-gnome-xsession-33.png
new file mode 100644
index 0000000..1b8becc
Binary files /dev/null and b/tests/references/pixelate-open-gnome-xsession-33.png differ
diff --git a/tests/references/pixelate-open-gnome-xsession-34.png b/tests/references/pixelate-open-gnome-xsession-34.png
new file mode 100644
index 0000000..1eff756
Binary files /dev/null and b/tests/references/pixelate-open-gnome-xsession-34.png differ
diff --git a/tests/references/pixelate-open-gnome-xsession-35.png b/tests/references/pixelate-open-gnome-xsession-35.png
new file mode 100644
index 0000000..1eff756
Binary files /dev/null and b/tests/references/pixelate-open-gnome-xsession-35.png differ
diff --git a/tests/references/pixelate-open-gnome-xsession-36.png b/tests/references/pixelate-open-gnome-xsession-36.png
new file mode 100644
index 0000000..9a8c78f
Binary files /dev/null and b/tests/references/pixelate-open-gnome-xsession-36.png differ
diff --git a/tests/run-test.sh b/tests/run-test.sh
index 38c9dd4..7a3e1b8 100755
--- a/tests/run-test.sh
+++ b/tests/run-test.sh
@@ -200,6 +200,7 @@ test_effect "energize-b"
test_effect "fire"
test_effect "hexagon"
test_effect "incinerate"
+test_effect "pixelate"
test_effect "tv"
test_effect "wisps"