{"id":19200269,"url":"https://github.com/lommix/bevy_enoki","last_synced_at":"2025-04-05T08:03:46.894Z","repository":{"id":230552832,"uuid":"778741472","full_name":"Lommix/bevy_enoki","owner":"Lommix","description":"2D particle system with custom material traits. Works well in wasm webgl2 and mobile","archived":false,"fork":false,"pushed_at":"2024-12-08T23:20:20.000Z","size":15055,"stargazers_count":59,"open_issues_count":1,"forks_count":5,"subscribers_count":2,"default_branch":"master","last_synced_at":"2025-03-29T07:02:20.560Z","etag":null,"topics":["2d","bevy","graphics","particles"],"latest_commit_sha":null,"homepage":"","language":"Rust","has_issues":true,"has_wiki":null,"has_pages":null,"mirror_url":null,"source_name":null,"license":"apache-2.0","status":null,"scm":"git","pull_requests_enabled":true,"icon_url":"https://github.com/Lommix.png","metadata":{"files":{"readme":"README.md","changelog":"CHANGELOG.md","contributing":null,"funding":null,"license":"LICENSE-APACHE","code_of_conduct":null,"threat_model":null,"audit":null,"citation":null,"codeowners":null,"security":null,"support":null,"governance":null,"roadmap":null,"authors":null,"dei":null,"publiccode":null,"codemeta":null}},"created_at":"2024-03-28T10:05:50.000Z","updated_at":"2025-03-25T15:09:35.000Z","dependencies_parsed_at":"2024-11-07T15:26:09.655Z","dependency_job_id":"9bad24a5-9e5e-4956-952a-1b27cde7cdb4","html_url":"https://github.com/Lommix/bevy_enoki","commit_stats":{"total_commits":57,"total_committers":3,"mean_commits":19.0,"dds":0.03508771929824561,"last_synced_commit":"a38b9e835a6653774c28c754f321249e57590101"},"previous_names":["lommix/bevy_enoki"],"tags_count":2,"template":false,"template_full_name":null,"repository_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/Lommix%2Fbevy_enoki","tags_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/Lommix%2Fbevy_enoki/tags","releases_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/Lommix%2Fbevy_enoki/releases","manifests_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/Lommix%2Fbevy_enoki/manifests","owner_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/owners/Lommix","download_url":"https://codeload.github.com/Lommix/bevy_enoki/tar.gz/refs/heads/master","host":{"name":"GitHub","url":"https://github.com","kind":"github","repositories_count":247305932,"owners_count":20917208,"icon_url":"https://github.com/github.png","version":null,"created_at":"2022-05-30T11:31:42.601Z","updated_at":"2022-07-04T15:15:14.044Z","host_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub","repositories_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories","repository_names_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repository_names","owners_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/owners"}},"keywords":["2d","bevy","graphics","particles"],"created_at":"2024-11-09T12:31:38.982Z","updated_at":"2025-04-05T08:03:46.878Z","avatar_url":"https://github.com/Lommix.png","language":"Rust","funding_links":[],"categories":[],"sub_categories":[],"readme":"\u003cdiv style=\"display:flex;gap:1rem;\"\u003e\n    \u003cimg src=\"docs/icon.png\" width=\"45\" height=\"64\"\u003e\n    \u003ch1 style=\"border:none\"\u003eBevy Enoki\u003c/h1\u003e\n\u003c/div\u003e\n\n[![License: MIT or Apache 2.0](https://img.shields.io/badge/License-MIT%20or%20Apache2-blue.svg)](./LICENSE)\n[![Crate](https://img.shields.io/crates/v/bevy_enoki.svg)](https://crates.io/crates/bevy_enoki)\n\nEnoki - A 2D particle system for the Bevy game engine.\n\n![animation](docs/output.gif)\n\n## Overview\n\nThe Enoki particle system is a CPU calculate particle system, that uses GPU Instancing and works well in `wasm` and mobile.\nYou have access to a `Material Trait` which let's you implement your own\nfragment shaders on top. Resulting in a powerful tool to build any modern VFX effect.\n\nAdditionally, spawner configuration are provided via `ron` files, which can be hot reloaded.\nThe default material allows not only for custom textures, but also sprite sheet animations over the particle lifetime.\n\n## Compatibility\n\n| bevy | bevy_enoki |\n| ---: | ---------: |\n| 0.15 |      0.3.3 |\n| 0.14 |      0.2.2 |\n| 0.13 |        0.1 |\n\n## Editor\n\nEnoki has a feature rich Editor.\n\n![editor](docs/editor.jpg)\n\n- load and save effect assets.\n- watch a shader file with hot reload, your editor of choice.\n- load a texture.\n- play with values.\n\nGet started by installing it via cargo\n```\ncargo install enoki2d_editor\n```\n\n---\n\n## Examples\n\n```shell\ncargo run -p example --bin material\ncargo run -p example --bin sprites\ncargo run -p example --bin dynamic\n```\n\n## Usage\n\nAdd the `bevy_enoki` dependency to your `Cargo.toml`\n\n```toml\nbevy_enoki = \"0.2.2\"\n```\n\nAdd the `EnokiPlugin` to your app\n\n```rust\nApp::new()\n    .add_plugins(DefaultPlugins)\n    .add_plugins(EnokiPlugin)\n    .run()\n```\n\nCreate your first particle spawner.\n\n```rust\nuse bevy_enoki::prelude::*;\n\nfn setup(\n    mut cmd : Commands,\n    mut materials: ResMut\u003cAssets\u003cSpriteParticle2dMaterial\u003e\u003e,\n    server : Res\u003cAssetServer\u003e,\n){\n    cmd.spawn(Camera2dBundle::default());\n\n    // minimal setup\n    // white quads with a default effect\n    cmd.spawn(\n        // the main component.\n        // holds a material handle.\n        // defaults to a simple white color quad.\n        // has required components\n        ParticleSpawner::default()\n    )\n\n    // bring in your own effect asset from a ron file\n    // (hot reload by default)\n    cmd.spawn((\n        ParticleSpawner::default(),\n        // the effect components holds the baseline\n        // effect asset.\n        ParticleEffectHandle(server.load(\"firework.particle.ron\")),\n    ));\n\n\n    // now with a sprite sheet animation over lifetime\n    let sprite_material = materials.add(\n        // the other args (hframes and vframes) defines how the sprite sheet is divided for animating,\n        // you can also just use `form_texture` for a single sprite\n        SpriteParticle2dMaterial::new(server.load(\"particle.png\"), 6, 1),\n    );\n\n    cmd.spawn((\n        ParticleSpawner(sprite_material),\n        ParticleEffectHandle(server.load(\"firework.particle.ron\")),\n    ));\n}\n```\n\n## Control your particles\n\nThere 4 main components you can play with. These are required by the `ParticleSpawner`\nand thus added, if not provided.\n\n- `ParticleSpawnerState`: Controls the spawner state.\n- `ParticleEffectInstance`: A unique clone of the effect. Can be changed at runtime, only affects the spawner attached to. Will reload, when the asset changes.\n- `ParticleEffectHandle`: A link the main effect asset.\n- `ParticleStore`: Holds the particle data. You mostly won't interact with this.\n- `OneShot`: A optional Tag component. That will either deactivate or delete the spawner, after first burst is done.\n- `NoAutoAabb`: Opt out of auto Aabb calculation.\n\n## Create a custom Material\n\nJust like any other Bevy material, you can define your own\nfragment shader.\n\n```rust\n#[derive(AsBindGroup, Asset, TypePath, Clone, Default)]\npub struct FireParticleMaterial {\n    #[texture(0)]\n    #[sampler(1)]\n    texture: Handle\u003cImage\u003e,\n}\n\nimpl Particle2dMaterial for FireParticleMaterial {\n    fn fragment_shader() -\u003e bevy::render::render_resource::ShaderRef {\n        \"custom_material.wgsl\".into()\n    }\n}\n\nfn setup(){\n    App::default()\n        .add_plugins(DefaultPlugins)\n        .add_plugins(EnokiPlugin)\n        .add_plugins(Particle2dMaterialPlugin::\u003cFireParticleMaterial\u003e::default())\n        .run()\n}\n```\n\n## Create a shader\n\n```wgsl\n//assets/custom_material.wgsl\n#import bevy_enoki::particle_vertex_out::{ VertexOutput }\n\n@group(1) @binding(0) var texture: texture_2d\u003cf32\u003e;\n@group(1) @binding(1) var texture_sampler: sampler;\n\n\n@fragment\nfn fragment(in: VertexOutput) -\u003e @location(0) vec4\u003cf32\u003e {\n    var out = in.color\n    // go wild\n    return out;\n}\n```\n\nThat's it, now add the Material to your Spawner! These are the values provided by the vertex shader:\n\n```wgsl\nstruct VertexOutput {\n  @builtin(position) clip_position: vec4\u003cf32\u003e,\n  @location(0) @interpolate(flat) color: vec4\u003cf32\u003e,\n  @location(1) uv : vec2\u003cf32\u003e,\n  @location(2) lifetime_frac : f32,\n  @location(3) lifetime_total : f32,\n};\n```\n\n## The Effect Asset\n\n[Here is a default ron config](example/assets/base.particle.ron)\n\n```rust\n#[derive(Deserialize, Default, Clone, Debug)]\npub enum EmissionShape {\n    #[default]\n    Point,\n    Circle(f32),\n}\n\n#[derive(Asset, TypePath, Default, Deserialize, Clone, Debug)]\npub struct Particle2dEffect {\n    pub spawn_rate: f32,\n    pub spawn_amount: u32,\n    pub emission_shape: EmissionShape,\n    pub lifetime: Rval\u003cf32\u003e,\n    pub linear_speed: Option\u003cRval\u003cf32\u003e\u003e,\n    pub linear_acceleration: Option\u003cRval\u003cf32\u003e\u003e,\n    pub direction: Option\u003cRval\u003cVec2\u003e\u003e,\n    pub angular_speed: Option\u003cRval\u003cf32\u003e\u003e,\n    pub angular_acceleration: Option\u003cRval\u003cf32\u003e\u003e,\n    pub scale: Option\u003cRval\u003cf32\u003e\u003e,\n    pub color: Option\u003cLinearRgba\u003e,\n    pub gravity_direction: Option\u003cRval\u003cVec2\u003e\u003e,\n    pub gravity_speed: Option\u003cRval\u003cf32\u003e\u003e,\n    pub linear_damp: Option\u003cRval\u003cf32\u003e\u003e,\n    pub angular_damp: Option\u003cRval\u003cf32\u003e\u003e,\n    pub scale_curve: Option\u003cMultiCurve\u003cf32\u003e\u003e,\n    pub color_curve: Option\u003cMultiCurve\u003cLinearRgba\u003e\u003e,\n}\n```\n\nThis how you create a `MultiCurve`. Currently, Supports `LinearRgba` and `f32`.\n`RVal` stands for any Value with a randomness property between 0 - 1.\n\n```rust\nlet curve = MultiCurve::new()\n    .with_point(LinearRgba::RED, 0.0, None)\n    .with_point(LinearRgba::BLUE, 1.0, Some(EaseFunction::SineInOut));\n\n// max 1.0, randomness of 0.1 (0.9 - 1.1)\nlet rval = Rval::new(1.0, 0.1);\n```\n","project_url":"https://awesome.ecosyste.ms/api/v1/projects/github.com%2Flommix%2Fbevy_enoki","html_url":"https://awesome.ecosyste.ms/projects/github.com%2Flommix%2Fbevy_enoki","lists_url":"https://awesome.ecosyste.ms/api/v1/projects/github.com%2Flommix%2Fbevy_enoki/lists"}