AgentStack
SKILL verified MIT Self-run

Bevy Ecs Queries

skill-chrisgliddon-bevy-skills-bevy-ecs-queries · by chrisgliddon

Use when writing `Query<D, F>` with filters like `With`/`Without`/`Or`, detecting changes with `Changed<T>`/`Added<T>`, parallelising with `par_iter`/`par_iter_mut`, building a query lens with `transmute_lens`, or hitting the new 0.18 `ArchetypeQueryData` bound. Covers Bevy 0.18 query patterns.

No reviews yet
0 installs
12 views
0.0% view→install

Install

$ agentstack add skill-chrisgliddon-bevy-skills-bevy-ecs-queries

✓ scanned · ✓ verified — works with Claude Code, Cursor, and more.

Security review

✓ Passed

No issues found. Passed automated security review. · v0.1.0 How review works →

  • Prompt-injection patterns
  • Secret / credential exfiltration
  • Dangerous shell & filesystem operations
  • Untrusted network calls
  • Known-malicious package signatures

What it can access

  • Network access No
  • Filesystem access No
  • Shell / process execution No
  • Environment & secrets No
  • Dynamic code execution No

From automated source analysis of v0.1.0. “Used” means the capability is present in the source — more access means more to trust, not that it’s unsafe.

Are you the author of Bevy Ecs Queries? Claim this listing to set pricing, connect Stripe payouts, and keep 70% of every sale.
Sign up to claim

About

Bevy 0.18 — ECS Queries

When to use this skill

  • Reading or writing components from a system.
  • Filtering by presence (With/Without), alternation (Or), or change detection (Changed/Added).
  • Parallelising over a large entity set with par_iter_mut.
  • Borrowing a subset of a query via a lens (transmute_lens).
  • Compiler error mentioning ArchetypeQueryData (new bound in 0.18).

Canonical pattern

use bevy::prelude::*;

#[derive(Component, Default)]
struct Health(f32);

#[derive(Component, Default)]
struct Velocity(Vec3);

#[derive(Component)]
struct Player;

#[derive(Component)]
struct Enemy;

fn main() {
    App::new()
        .add_plugins(DefaultPlugins)
        .add_systems(Update, (
            move_things,
            on_health_changed,
            damage_visible_enemies,
            integrate_in_parallel,
        ))
        .run();
}

// Sequential iteration. `&` for read, `&mut` for write.
fn move_things(time: Res, mut q: Query) {
    let dt = time.delta_secs();
    for (vel, mut tf) in &mut q {
        tf.translation += vel.0 * dt;
    }
}

// Change detection. `Changed` triggers on insert OR mutation.
// `Added` triggers only on insert.
fn on_health_changed(q: Query>) {
    for (entity, hp) in &q {
        info!("entity {:?} now has {} hp", entity, hp.0);
    }
}

// Combined filters. `With`/`Without` constrain entities;
// `Or` alternates over filters (not components).
fn damage_visible_enemies(
    mut q: Query, Without, Or, Changed)>)>,
) {
    for mut hp in &mut q {
        hp.0 -= 1.0;
    }
}

// Parallel iteration. Use when N is large (>10k) and per-entity work is non-trivial.
// Cannot use `Commands` or external mutable state — task pool runs items in parallel.
fn integrate_in_parallel(mut q: Query) {
    q.par_iter_mut().for_each(|(vel, mut tf)| {
        tf.translation += vel.0 * 0.016;
    });
}

// Query lens: temporarily view a query as a narrower one. Useful for
// passing a stricter query into a helper without re-binding the system's
// SystemParam list.
#[allow(dead_code)]
fn use_lens(mut q: Query) {
    // Read-only narrowed view of just the Transform column.
    let mut lens = q.transmute_lens::();
    let _read_only: Query = lens.query();
}

Gotchas (0.18)

  • ArchetypeQueryData is a new trait that bounds query data types where the exact item count must be known at compile time (e.g. for_each-style ergonomics). If you get a "trait ArchetypeQueryData not implemented" error, you're using a dynamic query (FilteredEntityRef/FilteredEntityMut) where a static one is required. Re-shape the query.
  • EntityMut::get_components_mut::() is the safe way to grab two &muts out of one entity in 0.18 — returns Result. Don't reach for unsafe World::get_mut aliasing tricks.
  • Query::get/get_mut returns Result, not Option. The error type carries the entity, so don't swallow it with .ok() if you actually need to know why a lookup missed.
  • Or, With)>Or alternates over filters, not raw component types. Or does not compile.
  • Changed/Added are tick-based. A system that runs every other frame can miss changes only seen in the skipped frame. If you must not miss a change, use observers or a buffered queue.
  • Don't pair par_iter_mut with Commands. Spawn/despawn from a sequential system that consumes a Resource queue written by the parallel one.

See also

  • bevy-ecs-components — declaring the components queried here.
  • bevy-ecs-systems — using queries inside SystemParam and run conditions.
  • bevy-migration-0-17-to-0-18EntityMut::get_components_mut and tick-type move.

Source & license

This open-source skill is cataloged on AgentStack and links to its original source — we do not rehost the code.

Install and usage instructions live in the source repository linked above.

Reviews

No reviews yet — be the first.

Versions

  • v0.1.0 Imported from the upstream source.