diff options
Diffstat (limited to 'docs/wiki/Configuration:-Animations.md')
| -rw-r--r-- | docs/wiki/Configuration:-Animations.md | 412 |
1 files changed, 412 insertions, 0 deletions
diff --git a/docs/wiki/Configuration:-Animations.md b/docs/wiki/Configuration:-Animations.md new file mode 100644 index 00000000..2400f568 --- /dev/null +++ b/docs/wiki/Configuration:-Animations.md @@ -0,0 +1,412 @@ +### Overview + +Niri has several animations which you can configure in the same way. +Additionally, you can disable or slow down all animations at once. + +Here's a quick glance at the available animations with their default values. + +```kdl +animations { + // Uncomment to turn off all animations. + // You can also put "off" into each individual animation to disable it. + // off + + // Slow down all animations by this factor. Values below 1 speed them up instead. + // slowdown 3.0 + + // Individual animations. + + workspace-switch { + spring damping-ratio=1.0 stiffness=1000 epsilon=0.0001 + } + + window-open { + duration-ms 150 + curve "ease-out-expo" + } + + window-close { + duration-ms 150 + curve "ease-out-quad" + } + + horizontal-view-movement { + spring damping-ratio=1.0 stiffness=800 epsilon=0.0001 + } + + window-movement { + spring damping-ratio=1.0 stiffness=800 epsilon=0.0001 + } + + window-resize { + spring damping-ratio=1.0 stiffness=800 epsilon=0.0001 + } + + config-notification-open-close { + spring damping-ratio=0.6 stiffness=1000 epsilon=0.001 + } + + screenshot-ui-open { + duration-ms 200 + curve "ease-out-quad" + } + + overview-open-close { + spring damping-ratio=1.0 stiffness=800 epsilon=0.0001 + } +} +``` + +### Animation Types + +There are two animation types: easing and spring. +Each animation can be either an easing or a spring. + +#### Easing + +This is a relatively common animation type that changes the value over a set duration using an interpolation curve. + +To use this animation, set the following parameters: + +- `duration-ms`: duration of the animation in milliseconds. +- `curve`: the easing curve to use. + +```kdl +animations { + window-open { + duration-ms 150 + curve "ease-out-expo" + } +} +``` + +Currently, niri only supports four curves: + +- `ease-out-quad` <sup>Since: 0.1.5</sup> +- `ease-out-cubic` +- `ease-out-expo` +- `linear` <sup>Since: 0.1.6</sup> + +You can get a feel for them on pages like [easings.net](https://easings.net/). + +#### Spring + +Spring animations use a model of a physical spring to animate the value. +They notably feel better with touchpad gestures, because they take into account the velocity of your fingers as you release the swipe. +Springs can also oscillate / bounce at the end with the right parameters if you like that sort of thing, but they don't have to (and by default they mostly don't). + +Due to springs using a physical model, the animation parameters are less obvious and generally should be tuned with trial and error. +Notably, you cannot directly set the duration. +You can use the [Elastic](https://flathub.org/apps/app.drey.Elastic) app to help visualize how the spring parameters change the animation. + +A spring animation is configured like this, with three mandatory parameters: + +```kdl +animations { + workspace-switch { + spring damping-ratio=1.0 stiffness=1000 epsilon=0.0001 + } +} +``` + +The `damping-ratio` goes from 0.1 to 10.0 and has the following properties: + +- below 1.0: underdamped spring, will oscillate in the end. +- above 1.0: overdamped spring, won't oscillate. +- 1.0: critically damped spring, comes to rest in minimum possible time without oscillations. + +However, even with damping ratio = 1.0, the spring animation may oscillate if "launched" with enough velocity from a touchpad swipe. + +> [!WARNING] +> Overdamped springs currently have some numerical stability issues and may cause graphical glitches. +> Therefore, setting `damping-ratio` above `1.0` is not recommended. + +Lower `stiffness` will result in a slower animation more prone to oscillation. + +Set `epsilon` to a lower value if the animation "jumps" at the end. + +> [!TIP] +> The spring *mass* (which you can see in Elastic) is hardcoded to 1.0 and cannot be changed. +> Instead, change `stiffness` proportionally. +> E.g. increasing mass by 2× is the same as decreasing stiffness by 2×. + +### Animations + +Now let's go into more detail on the animations that you can configure. + +#### `workspace-switch` + +Animation when switching workspaces up and down, including after the vertical touchpad gesture (a spring is recommended). + +```kdl +animations { + workspace-switch { + spring damping-ratio=1.0 stiffness=1000 epsilon=0.0001 + } +} +``` + +#### `window-open` + +Window opening animation. + +This one uses an easing type by default. + +```kdl +animations { + window-open { + duration-ms 150 + curve "ease-out-expo" + } +} +``` + +##### `custom-shader` + +<sup>Since: 0.1.6</sup> + +You can write a custom shader for drawing the window during an open animation. + +See [this example shader](./examples/open_custom_shader.frag) for a full documentation with several animations to experiment with. + +If a custom shader fails to compile, niri will print a warning and fall back to the default, or previous successfully compiled shader. +When running niri as a systemd service, you can see the warnings in the journal: `journalctl -ef /usr/bin/niri` + +> [!WARNING] +> +> Custom shaders do not have a backwards compatibility guarantee. +> I may need to change their interface as I'm developing new features. + +Example: open will fill the current geometry with a solid gradient that gradually fades in. + +```kdl +animations { + window-open { + duration-ms 250 + curve "linear" + + custom-shader r" + vec4 open_color(vec3 coords_geo, vec3 size_geo) { + vec4 color = vec4(0.0); + + if (0.0 <= coords_geo.x && coords_geo.x <= 1.0 + && 0.0 <= coords_geo.y && coords_geo.y <= 1.0) + { + vec4 from = vec4(1.0, 0.0, 0.0, 1.0); + vec4 to = vec4(0.0, 1.0, 0.0, 1.0); + color = mix(from, to, coords_geo.y); + } + + return color * niri_clamped_progress; + } + " + } +} +``` + +#### `window-close` + +<sup>Since: 0.1.5</sup> + +Window closing animation. + +This one uses an easing type by default. + +```kdl +animations { + window-close { + duration-ms 150 + curve "ease-out-quad" + } +} +``` + +##### `custom-shader` + +<sup>Since: 0.1.6</sup> + +You can write a custom shader for drawing the window during a close animation. + +See [this example shader](./examples/close_custom_shader.frag) for a full documentation with several animations to experiment with. + +If a custom shader fails to compile, niri will print a warning and fall back to the default, or previous successfully compiled shader. +When running niri as a systemd service, you can see the warnings in the journal: `journalctl -ef /usr/bin/niri` + +> [!WARNING] +> +> Custom shaders do not have a backwards compatibility guarantee. +> I may need to change their interface as I'm developing new features. + +Example: close will fill the current geometry with a solid gradient that gradually fades away. + +```kdl +animations { + window-close { + custom-shader r" + vec4 close_color(vec3 coords_geo, vec3 size_geo) { + vec4 color = vec4(0.0); + + if (0.0 <= coords_geo.x && coords_geo.x <= 1.0 + && 0.0 <= coords_geo.y && coords_geo.y <= 1.0) + { + vec4 from = vec4(1.0, 0.0, 0.0, 1.0); + vec4 to = vec4(0.0, 1.0, 0.0, 1.0); + color = mix(from, to, coords_geo.y); + } + + return color * (1.0 - niri_clamped_progress); + } + " + } +} +``` + +#### `horizontal-view-movement` + +All horizontal camera view movement animations, such as: + +- When a window off-screen is focused and the camera scrolls to it. +- When a new window appears off-screen and the camera scrolls to it. +- After a horizontal touchpad gesture (a spring is recommended). + +```kdl +animations { + horizontal-view-movement { + spring damping-ratio=1.0 stiffness=800 epsilon=0.0001 + } +} +``` + +#### `window-movement` + +<sup>Since: 0.1.5</sup> + +Movement of individual windows within a workspace. + +Includes: + +- Moving window columns with `move-column-left` and `move-column-right`. +- Moving windows inside a column with `move-window-up` and `move-window-down`. +- Moving windows out of the way upon window opening and closing. +- Window movement between columns when consuming/expelling. + +This animation *does not* include the camera view movement, such as scrolling the workspace left and right. + +```kdl +animations { + window-movement { + spring damping-ratio=1.0 stiffness=800 epsilon=0.0001 + } +} +``` + +#### `window-resize` + +<sup>Since: 0.1.5</sup> + +Window resize animation. + +Only manual window resizes are animated, i.e. when you resize the window with `switch-preset-column-width` or `maximize-column`. +Also, very small resizes (up to 10 pixels) are not animated. + +```kdl +animations { + window-resize { + spring damping-ratio=1.0 stiffness=800 epsilon=0.0001 + } +} +``` + +##### `custom-shader` + +<sup>Since: 0.1.6</sup> + +You can write a custom shader for drawing the window during a resize animation. + +See [this example shader](./examples/resize_custom_shader.frag) for a full documentation with several animations to experiment with. + +If a custom shader fails to compile, niri will print a warning and fall back to the default, or previous successfully compiled shader. +When running niri as a systemd service, you can see the warnings in the journal: `journalctl -ef /usr/bin/niri` + +> [!WARNING] +> +> Custom shaders do not have a backwards compatibility guarantee. +> I may need to change their interface as I'm developing new features. + +Example: resize will show the next (after resize) window texture right away, stretched to the current geometry. + +```kdl +animations { + window-resize { + custom-shader r" + vec4 resize_color(vec3 coords_curr_geo, vec3 size_curr_geo) { + vec3 coords_tex_next = niri_geo_to_tex_next * coords_curr_geo; + vec4 color = texture2D(niri_tex_next, coords_tex_next.st); + return color; + } + " + } +} +``` + +#### `config-notification-open-close` + +The open/close animation of the config parse error and new default config notifications. + +This one uses an underdamped spring by default (`damping-ratio=0.6`) which causes a slight oscillation in the end. + +```kdl +animations { + config-notification-open-close { + spring damping-ratio=0.6 stiffness=1000 epsilon=0.001 + } +} +``` + +#### `screenshot-ui-open` + +<sup>Since: 0.1.8</sup> + +The open (fade-in) animation of the screenshot UI. + +```kdl +animations { + screenshot-ui-open { + duration-ms 200 + curve "ease-out-quad" + } +} +``` + +#### `overview-open-close` + +<sup>Since: 25.05</sup> + +The open/close zoom animation of the [Overview](./Overview.md). + +```kdl +animations { + overview-open-close { + spring damping-ratio=1.0 stiffness=800 epsilon=0.0001 + } +} +``` + +### Synchronized Animations + +<sup>Since: 0.1.5</sup> + +Sometimes, when two animations are meant to play together synchronized, niri will drive them both with the same configuration. + +For example, if a window resize causes the view to move, then that view movement animation will also use the `window-resize` configuration (rather than the `horizontal-view-movement` configuration). +This is especially important for animated resizes to look good when using `center-focused-column "always"`. + +As another example, resizing a window in a column vertically causes other windows to move up or down into their new position. +This movement will use the `window-resize` configuration, rather than the `window-movement` configuration, to keep the animations synchronized. + +A few actions are still missing this synchronization logic, since in some cases it is difficult to implement properly. +Therefore, for the best results, consider using the same parameters for related animations (they are all the same by default): + +- `horizontal-view-movement` +- `window-movement` +- `window-resize` |
