Back to rankings

djeedai/bevy_hanabi

Rust

πŸŽ† Hanabi β€” a GPU particle system plugin for the Bevy game engine.

rustparticleparticlesvfxbevybevy-plugingpu-particleseffectsgamedev
Star Growth
Stars
1.4k
Forks
119
Weekly Growth
β€”
Issues
40
5001k
Jan 2023Mar 2024May 2025Jul 2026
Artifactscrates.iocargo add bevy_hanabi
README

πŸŽ† Bevy Hanabi

License: MIT or Apache 2.0 Doc Crate Build Status Coverage Status Bevy tracking

πŸŽ† Hanabi β€” a GPU particle system for the Bevy game engine.

firework

Overview

The Hanabi particle system is a modern GPU-based particle system for the Bevy game engine. It focuses on scale to produce stunning visual effects (VFX) in real time, offloading most of the work to the GPU, with minimal CPU intervention. The design is inspired by modern particle systems found in other industry-leading game engines.

🚧 This project is under heavy development, and is currently lacking both features and performance / usability polish. However, for moderate-size effects, it can already be used in your project. Feedback and contributions on both design and features are very much welcome.

πŸŽ† Hanabi makes heavy use of compute shaders to offload work to the GPU in a performant way. Support for compute shaders on the wasm target (WebAssembly) is available as of v0.13 (Bevy 0.14), and only through WebGPU. See the WebAssembly support documentation for details.

Usage

The πŸŽ† Bevy Hanabi plugin is compatible with Bevy versions >= 0.6; see Compatible Bevy versions.

Add the dependency

Add the bevy_hanabi dependency to Cargo.toml:

[dependencies]
bevy_hanabi = "0.19"

See also Features below for the list of supported features.

System setup

Add the HanabiPlugin to your app:

use bevy_hanabi::prelude::*;

App::default()
    .add_plugins(DefaultPlugins)
    .add_plugins(HanabiPlugin)
    .run();

Create an effect asset

Create an EffectAsset describing a visual effect:

fn setup(mut effects: ResMut<Assets<EffectAsset>>) {
  // Define a color gradient from red to transparent black
  let mut gradient = Gradient::new();
  gradient.add_key(0.0, Vec4::new(1., 0., 0., 1.));
  gradient.add_key(1.0, Vec4::splat(0.));

  // Create a new expression module
  let mut module = Module::default();

  // On spawn, randomly initialize the position of the particle
  // to be over the surface of a sphere of radius 2 units.
  let init_pos = SetPositionSphereModifier {
      center: module.lit(Vec3::ZERO),
      radius: module.lit(2.),
      dimension: ShapeDimension::Surface,
  };

  // Also initialize a radial initial velocity to 6 units/sec
  // away from the (same) sphere center.
  let init_vel = SetVelocitySphereModifier {
      center: module.lit(Vec3::ZERO),
      speed: module.lit(6.),
  };

  // Initialize the total lifetime of the particle, that is
  // the time for which it's simulated and rendered. This modifier
  // is almost always required, otherwise the particles won't show.
  let lifetime = module.lit(10.); // literal value "10.0"
  let init_lifetime = SetAttributeModifier::new(
      Attribute::LIFETIME, lifetime);

  // Every frame, add a gravity-like acceleration downward
  let accel = module.lit(Vec3::new(0., -3., 0.));
  let update_accel = AccelModifier::new(accel);

  // Create the effect asset
  let effect = EffectAsset::new(
    // Maximum number of particles alive at a time
    1024,
    // Spawn at a rate of 5 particles per second
    SpawnerSettings::rate(5.0.into()),
    // Move the expression module into the asset
    module
  )
  .with_name("MyEffect")
  .init(init_pos)
  .init(init_vel)
  .init(init_lifetime)
  .update(update_accel)
  // Render the particles with a color gradient over their
  // lifetime. This maps the gradient key 0 to the particle spawn
  // time, and the gradient key 1 to the particle death (10s).
  .render(ColorOverLifetimeModifier { gradient, ..default() });

  // Insert into the asset system
  let effect_handle = effects.add(effect);
}

Spawn a particle effect

Use a ParticleEffect to create an effect instance from an existing asset.

commands.spawn((
    ParticleEffect::new(effect_handle),
    Transform::from_translation(Vec3::Y),
));

Examples

See the examples/ folder.

A web demo (using the WebAssembly target) showing all examples is availabe in the examples/wasm/ folder. You can open index.html in any browser to see a GIF of all the examples. Running the actual WebAssembly example however requires serving the files with an HTTP server. If you have NodeJS installed, you can do that for example by running npx http-server examples/wasm.

Note for Linux users: The examples build with the bevy/x11 feature by default to enable support for the X11 display server. If you want to use the Wayland display server instead, add the bevy/wayland feature.

Feature List

This list contains the major fixed features provided by πŸŽ† Hanabi. Beyond that, with the power of the Expressions API, visual effect authors can further customize their effects by assigning individual particle attributes (position, color, etc.).

  • Spawn
    • Constant rate
    • One-time burst
    • Repeated burst
    • Spawner resetting
    • Spawner activation/deactivation
    • Randomized spawning parameters
  • Initialize
    • Constant position
    • Position over shape
      • cube
      • circle
      • sphere
      • cone / truncated cone (3D)
      • plane
      • generic mesh / point cloud (?)
    • Random position offset
    • Velocity over shape (with random speed)
      • circle
      • sphere
      • tangent
    • Constant/random per-particle color
    • Constant/random per-particle size
    • Constant/random par-particle age and lifetime
  • Update
    • Simulation condition
      • Always, even when hidden
      • Only when visible
    • Motion integration (Euler)
    • Apply forces and accelerations
      • Constant acceleration (gravity)
      • Radial acceleration
      • Tangent acceleration
      • Force field
      • Linear drag
    • Collision
      • Shape
        • plane
        • cube
        • sphere
      • Depth buffer
    • Allow/deny despawn box
    • Lifetime
    • Size change over lifetime
    • Color change over lifetime
  • Render
    • Quad
      • Textured
    • Generic 3D mesh
    • Deformation
      • Stretch alongside velocity
      • Trails / Ribbons
    • Camera support
      • Render layers
      • 2D cameras (Camera2d) only
      • 3D cameras (Camera3d) only
      • Simultaneous dual 2D/3D cameras
      • Multiple viewports (split screen)
      • HDR camera and bloom
    • Size and orient particles
      • Face camera (Billboard)
      • Face constant direction
      • Orient alongside velocity
      • Screen-space size (projection independent)
  • Debug
    • GPU debug labels / groups
    • Debug visualization
      • Position magnitude
      • Velocity magnitude
      • Age / lifetime

Features

πŸŽ† Bevy Hanabi supports the following cargo features:

Feature Default Description
2d βœ” Enable rendering through 2D cameras (Camera2d)
3d βœ” Enable rendering through 3D cameras (Camera3d)

For optimization purpose, users of a single type of camera can disable the other type by skipping default features in their Cargo.toml. For example to use only the 3D mode:

bevy_hanabi = { version = "0.19", default-features = false, features = [ "3d" ] }

Compatible Bevy versions

The main branch is compatible with the latest Bevy release.

Compatibility of bevy_hanabi versions:

bevy_hanabi bevy
0.19 0.19
0.18 0.18
0.17 0.17
0.16 0.16
0.14-0.15 0.15
0.12-0.13 0.14
0.10-0.11 0.13
0.8-0.9 0.12
0.7 0.11
0.6 0.10
0.5 0.9
0.3-0.4 0.8
0.2 0.7
0.1 0.6

License

πŸŽ† Hanabi is dual-licensed under either:

at your option.

SPDX-License-Identifier: MIT OR Apache-2.0

Related repositories
farion1231/cc-switch

A cross-platform desktop All-in-One assistant for Claude Code, Codex, OpenCode, OpenClaw, Gemini CLI & Hermes Agent. Only official website: ccswitch.io

Rustcrates.ioMIT Licenseai-toolsclaude-code
ccswitch.io
119.4k8k
rustdesk/rustdesk

An open-source remote desktop application designed for self-hosting, as an alternative to TeamViewer.

Rustcrates.ioGNU Affero General Public License v3.0remote-controlremote-desktop
rustdesk.com
118.6k18.1k
rust-lang/rust

Empowering everyone to build reliable and efficient software.

Rustcrates.ioApache License 2.0rustcompiler
rust-lang.org
114.7k15.4k
tauri-apps/tauri

Build smaller, faster, and more secure desktop and mobile applications with a web frontend.

Rustcrates.ioApache License 2.0rustwebview
tauri.app
109.3k3.8k
denoland/deno

A modern runtime for JavaScript and TypeScript.

Rustcrates.ioMIT Licensedenotypescript
deno.com
107.8k6.2k
oven-sh/bun

Incredibly fast JavaScript runtime, bundler, test runner, and package manager – all in one

Rustcrates.ioOtherbunbundler
bun.com
94.9k4.9k
unionlabs/union

The trust-minimized, zero-knowledge bridging protocol, designed for censorship resistance, extremely high security, and usage in decentralized finance.

Rustcrates.ioApache License 2.0blockchaincosmos
union.build
73.9k3.9k
rtk-ai/rtk

CLI proxy that reduces LLM token consumption by 60-90% on common dev commands. Single Rust binary, zero dependencies

Rustcrates.ioApache License 2.0agentic-codingai-coding
rtk-ai.app
72.1k4.5k
toeverything/AFFiNE

There can be more than Notion and Miro. AFFiNE(pronounced [Ι™β€˜fain]) is a next-gen knowledge base that brings planning, sorting and creating all together. Privacy first, open-source, customizable and ready to use.

TypeScriptnpmOthereditorcrdt
affine.pro
70.6k5.1k
openinterpreter/openinterpreter

A coding agent for open models like Kimi K3

Rustcrates.ioApache License 2.0coding-agentdeepseek
openinterpreter.com
67k5.8k
BurntSushi/ripgrep

ripgrep recursively searches directories for a regex pattern while respecting your gitignore

Rustcrates.ioThe Unlicenseripgreprecursively-search
66.4k2.7k
alacritty/alacritty

A cross-platform, OpenGL terminal emulator.

Rustcrates.ioApache License 2.0terminal-emulatorsopengl
alacritty.org
65k3.5k