Animations with picom | www-gem words

www-gem words

Animations with picom

Published on

I’ve relied on Compositor in X11 for years to manage window transparency. My tiling manager doesn’t display borders or gaps, and I find decorations distracting. Initially, I used picom leveraging only its basic functionality. I’ve long considered animations counterproductive and visually taxing. However, I discovered that picom allows custom animation creation (you learn everyday with Linux). The level of customization offers both extensive personalization options and the ability to maintain a lightweight setup which piqued my interest.

╭── What kind of animations can I expect from picom?

There are numerous options available, making it impractical to list them all. Historically, picom had limitations, prompting the creation of several forks to implement additional features. Now, picom offers more capabilities and here is one random example of what to expect:

(source: https://www.youtube.com/watch?v=OsGrqilZr7A Yes, I just mentioned Odysee but have to use a youtube video)

╭── Stop talking and give me the code

Here is the code to add to your picom.conf file:

match = "window_type = 'normal'";
animations = (
        {
        triggers = ["close"];
        opacity = {
        curve = "cubic-bezier(0,1,1,1)";
        duration = 0.3;
        start = "window-raw-opacity-before";
        end = 0;
        };
        blur-opacity = "opacity";
        shadow-opacity = "opacity";

        scale-x = {
        curve = "cubic-bezier(0,1.3,1,1)";
        duration = 0.3;
        start = 1;
        end = 0.6;
        };
        scale-y = "scale-x";

        offset-x = "(1 - scale-x) / 2 * window-width";
        offset-y = "(1 - scale-y) / 2 * window-height";

        shadow-scale-x = "scale-x";
        shadow-scale-y = "scale-y";
        shadow-offset-x = "offset-x";
        shadow-offset-y = "offset-y";
        },

{
    triggers = ["open"];
    opacity = {
        curve = "cubic-bezier(0,1,1,1)";
        duration = 0.5;
        start = 0;
        end = "window-raw-opacity";
    };
    blur-opacity = "opacity";
    shadow-opacity = "opacity";

    scale-x = {
        curve = "cubic-bezier(0,1.3,1,1)";
        duration = 0.5;
        start = 0.6;
        end = 1;
    };
    scale-y = "scale-x";

    offset-x = "(1 - scale-x) / 2 * window-width";
    offset-y = "(1 - scale-y) / 2 * window-height";

    shadow-scale-x = "scale-x";
    shadow-scale-y = "scale-y";
    shadow-offset-x = "offset-x";
    shadow-offset-y = "offset-y";
},

{
    triggers = ["geometry"];
    scale-x = {
        curve = "cubic-bezier(0,0,0,1.28)";
        duration = 0.5;
        start = "window-width-before / window-width";
        end = 1;
    };

    scale-x-reverse = {
        curve = "cubic-bezier(0,0,0,1.28)";
        duration = 0.3;
        start = "window-width / window-width-before";
        end = 1;
    };
    scale-y = {
        curve = "cubic-bezier(0,0,0,1.28)";
        duration = 0.5;
        start = "window-height-before / window-height";
        end = 1;
    };
    scale-y-reverse = {
        curve = "cubic-bezier(0,0,0,1.28)";
        duration = 0.5;
        start = "window-height / window-height-before";
        end = 1;
    };
    offset-x = {
        curve = "cubic-bezier(0,0,0,1.28)";
        duration = 0.5;
        start = "window-x-before - window-x";
        end = 0;
    };
    offset-y = {
        curve = "cubic-bezier(0,0,0,1.28)";
        duration = 0.5;
        start = "window-y-before - window-y";
        end = 0;
    };
    shadow-scale-x = "scale-x";
    shadow-scale-y = "scale-y";
    shadow-offset-x = "offset-x";
    shadow-offset-y = "offset-y";
},
)

The basic structure is to use one of picom’s triggers to link an animation to a window’s event. Then you define the animation based on the window geometry (width, height, and position) and the “curve” (i.e.the visual effect). This is an example I found in an online dotfile . I’ve tweaked it to my liking and you can do the same.

╭── Bonus for the BSPWM users

Here is an additional piece of code to add an animation on workspace changes. Using the “show” trigger dedicated to minimized window seems to do the trick:

{
    triggers = ["show"];
    opacity = {
        curve = "cubic-bezier(0,1,1,1)";
        duration = 0.5;
        start = 0;
        end = "window-raw-opacity";
    };
    blur-opacity = "opacity";
    shadow-opacity = "opacity";

    scale-x = {
        curve = "cubic-bezier(0,1.3,1,1)";
        duration = 0.5;
        start = 0.6;
        end = 1;
    };
    scale-y = "scale-x";

    offset-x = "(1 - scale-x) / 2 * window-width";
    offset-y = "(1 - scale-y) / 2 * window-height";

    shadow-scale-x = "scale-x";
    shadow-scale-y = "scale-y";
    shadow-offset-x = "offset-x";
    shadow-offset-y = "offset-y";
},
    )

More food for thoughts? Check other posts about: #System


Thanks for your read. Hope it's been useful to you.


Interact with this post using Mastodon or

Comment on wwwgem's post

Copy and paste this URL into the search field of your favourite Fediverse app or the web interface of your Mastodon server.

✄ ┈ ┈ ┈ ┈ ┈ ┈ ┈ ┈ ┈ ┈ ┈ ┈ ┈ ┈ ┈ ┈ ┈ ┈ ┈ ┈ ┈ ┈ ┈ ┈ ┈ ┈ ┈