From 119d7acf096e70f7ddb910a8fe6a9ed7ac8e5793 Mon Sep 17 00:00:00 2001 From: Robert Garrett Date: Wed, 24 Dec 2025 14:54:49 -0600 Subject: [PATCH] WIP: Debug tool scans using Avian2d shape casting Working demonstration, but I'm not sure shape casting is the action I want to be doing. I've just found a "shape_intersections" method in the docs, but I'm saving my progress before making further changes. --- Cargo.lock | 304 ++++++++++++++++++++++++++++++++++++++++++-- Cargo.toml | 1 + src/birdoids/mod.rs | 3 + src/debug_plugin.rs | 38 ++++-- src/main.rs | 2 + 5 files changed, 321 insertions(+), 27 deletions(-) diff --git a/Cargo.lock b/Cargo.lock index 10d333fc..4e2eec40 100644 --- a/Cargo.lock +++ b/Cargo.lock @@ -105,6 +105,12 @@ dependencies = [ "memchr", ] +[[package]] +name = "allocator-api2" +version = "0.2.21" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "683d7910e743518b0e34f1186f92494becacb047c7b6bf616c96772180fef923" + [[package]] name = "alsa" version = "0.9.1" @@ -173,6 +179,7 @@ dependencies = [ name = "another-boids-in-rust" version = "0.7.0" dependencies = [ + "avian2d", "bevy", "bevy-inspector-egui", "bevy_spatial", @@ -339,6 +346,39 @@ version = "1.5.0" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "c08606f8c3cbf4ce6ec8e28fb0014a2c086708fe954eaa885384a6165172e7e8" +[[package]] +name = "avian2d" +version = "0.3.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "7133547d9cc068d527d91fdcb8c8017c89b26ce05dbd30daef9f1ca64824495d" +dependencies = [ + "arrayvec", + "avian_derive", + "bevy", + "bevy_heavy", + "bevy_math", + "bevy_transform_interpolation", + "bitflags 2.10.0", + "derive_more", + "itertools 0.13.0", + "nalgebra", + "parry2d", + "parry2d-f64", + "thread_local", +] + +[[package]] +name = "avian_derive" +version = "0.2.2" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "12b257f601a1535e0d4a7a7796f535e3a13de62fd422b16dff7c14d27f0d4048" +dependencies = [ + "proc-macro-error2", + "proc-macro2", + "quote", + "syn", +] + [[package]] name = "base64" version = "0.21.7" @@ -796,6 +836,16 @@ dependencies = [ "tracing", ] +[[package]] +name = "bevy_heavy" +version = "0.2.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "34ccc861fea2ff58c67f4df119512e204050bd7631a3a9c65e1a5e9d162cce28" +dependencies = [ + "bevy_math", + "bevy_reflect", +] + [[package]] name = "bevy_image" version = "0.16.1" @@ -1348,6 +1398,15 @@ dependencies = [ "thiserror 2.0.17", ] +[[package]] +name = "bevy_transform_interpolation" +version = "0.2.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "72c7c6c4e6a3d5415b3a29a17bd20c17cd0e2f068b96b24e263316d58d5346ea" +dependencies = [ + "bevy", +] + [[package]] name = "bevy_ui" version = "0.16.1" @@ -2115,6 +2174,15 @@ dependencies = [ "bytemuck", ] +[[package]] +name = "ena" +version = "0.14.3" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "3d248bdd43ce613d87415282f69b9bb99d947d290b10962dd6c56233312c2ad5" +dependencies = [ + "log", +] + [[package]] name = "encase" version = "0.10.0" @@ -2410,7 +2478,7 @@ version = "1.1.0" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "1bd49230192a3797a9a4d6abe9b3eed6f7fa4c8a8a4947977c6f80025f92cbd8" dependencies = [ - "rustix 1.1.2", + "rustix 1.1.3", "windows-link", ] @@ -2652,6 +2720,7 @@ version = "0.15.5" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "9229cfe53dfd69f0609a49f65461bd93001ea1ef889cd5529dd176593f5338a1" dependencies = [ + "allocator-api2", "equivalent", "foldhash", "serde", @@ -2999,6 +3068,16 @@ dependencies = [ "regex-automata", ] +[[package]] +name = "matrixmultiply" +version = "0.3.10" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "a06de3016e9fae57a36fd14dba131fccf49f74b40b7fbdb472f96e361ec71a08" +dependencies = [ + "autocfg", + "rawpointer", +] + [[package]] name = "memchr" version = "2.7.6" @@ -3098,6 +3177,34 @@ dependencies = [ "unicode-ident", ] +[[package]] +name = "nalgebra" +version = "0.33.2" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "26aecdf64b707efd1310e3544d709c5c0ac61c13756046aaaba41be5c4f66a3b" +dependencies = [ + "approx", + "glam", + "matrixmultiply", + "nalgebra-macros", + "num-complex", + "num-rational", + "num-traits", + "simba", + "typenum", +] + +[[package]] +name = "nalgebra-macros" +version = "0.2.2" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "254a5372af8fc138e36684761d3c0cdb758a4410e938babcff1c860ce14ddbfc" +dependencies = [ + "proc-macro2", + "quote", + "syn", +] + [[package]] name = "ndk" version = "0.8.0" @@ -3203,6 +3310,25 @@ dependencies = [ "windows-sys 0.61.2", ] +[[package]] +name = "num-bigint" +version = "0.4.6" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "a5e44f723f1133c9deac646763579fdb3ac745e418f2a7af9cd0c431da1f20b9" +dependencies = [ + "num-integer", + "num-traits", +] + +[[package]] +name = "num-complex" +version = "0.4.6" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "73f88a1307638156682bada9d7604135552957b7818057dcef22705b4d509495" +dependencies = [ + "num-traits", +] + [[package]] name = "num-derive" version = "0.4.2" @@ -3214,6 +3340,26 @@ dependencies = [ "syn", ] +[[package]] +name = "num-integer" +version = "0.1.46" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "7969661fd2958a5cb096e56c8e1ad0444ac2bbcd0061bd28660485a44879858f" +dependencies = [ + "num-traits", +] + +[[package]] +name = "num-rational" +version = "0.4.2" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "f83d14da390562dca69fc84082e73e548e1ad308d24accdedd2720017cb37824" +dependencies = [ + "num-bigint", + "num-integer", + "num-traits", +] + [[package]] name = "num-traits" version = "0.2.19" @@ -3638,6 +3784,58 @@ dependencies = [ "windows-link", ] +[[package]] +name = "parry2d" +version = "0.17.6" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "87edd53b1639e011e4765eecfceb0fa2c486da696dcdcfbc9a38bfc3574fb7e0" +dependencies = [ + "approx", + "arrayvec", + "bitflags 2.10.0", + "downcast-rs 1.2.1", + "either", + "ena", + "log", + "nalgebra", + "num-derive", + "num-traits", + "ordered-float 4.6.0", + "rayon", + "rustc-hash 2.1.1", + "simba", + "slab", + "smallvec", + "spade", + "thiserror 1.0.69", +] + +[[package]] +name = "parry2d-f64" +version = "0.17.6" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "42dadff562001ff51eed809d7c75ac6f185d8cffc575d7b45a8bdc6ea6f1bf30" +dependencies = [ + "approx", + "arrayvec", + "bitflags 2.10.0", + "downcast-rs 1.2.1", + "either", + "ena", + "log", + "nalgebra", + "num-derive", + "num-traits", + "ordered-float 4.6.0", + "rayon", + "rustc-hash 2.1.1", + "simba", + "slab", + "smallvec", + "spade", + "thiserror 1.0.69", +] + [[package]] name = "paste" version = "1.0.15" @@ -3728,7 +3926,7 @@ dependencies = [ "concurrent-queue", "hermit-abi", "pin-project-lite", - "rustix 1.1.2", + "rustix 1.1.3", "windows-sys 0.61.2", ] @@ -3790,6 +3988,28 @@ dependencies = [ "toml_edit 0.23.10+spec-1.0.0", ] +[[package]] +name = "proc-macro-error-attr2" +version = "2.0.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "96de42df36bb9bba5542fe9f1a054b8cc87e172759a1868aa05c1f3acc89dfc5" +dependencies = [ + "proc-macro2", + "quote", +] + +[[package]] +name = "proc-macro-error2" +version = "2.0.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "11ec05c52be0a07b08061f7dd003e7d7092e0472bc731b4af7bb1ef876109802" +dependencies = [ + "proc-macro-error-attr2", + "proc-macro2", + "quote", + "syn", +] + [[package]] name = "proc-macro2" version = "1.0.103" @@ -3908,6 +4128,12 @@ version = "0.6.2" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "20675572f6f24e9e76ef639bc5552774ed45f1c30e2951e1e99c59888861c539" +[[package]] +name = "rawpointer" +version = "0.2.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "60a357793950651c4ed0f3f52338f53b2f809f32d83a07f72909fa13e4c6c1e3" + [[package]] name = "rayon" version = "1.11.0" @@ -4006,6 +4232,12 @@ version = "1.1.0" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "19b30a45b0cd0bcca8037f3d0dc3421eaf95327a17cad11964fb8179b4fc4832" +[[package]] +name = "robust" +version = "1.2.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "4e27ee8bb91ca0adcf0ecb116293afa12d393f9c2b9b9cd54d33e8078fe19839" + [[package]] name = "rodio" version = "0.20.1" @@ -4061,9 +4293,9 @@ dependencies = [ [[package]] name = "rustix" -version = "1.1.2" +version = "1.1.3" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "cd15f8a2c5551a84d56efdc1cd049089e409ac19a3072d5037a17fd70719ff3e" +checksum = "146c9e247ccc180c1f61615433868c99f3de3ae256a30a43b49f67c2d9171f34" dependencies = [ "bitflags 2.10.0", "errno", @@ -4105,10 +4337,13 @@ dependencies = [ ] [[package]] -name = "ryu" -version = "1.0.21" +name = "safe_arch" +version = "0.7.4" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "62049b2877bf12821e8f9ad256ee38fdc31db7387ec2d3b3f403024de2034aea" +checksum = "96b02de82ddbe1b636e6170c21be622223aea188ef2e139be0a5b219ec215323" +dependencies = [ + "bytemuck", +] [[package]] name = "same-file" @@ -4188,15 +4423,15 @@ dependencies = [ [[package]] name = "serde_json" -version = "1.0.146" +version = "1.0.147" source = "registry+https://github.com/rust-lang/crates.io-index" -checksum = "217ca874ae0207aac254aa02c957ded05585a90892cc8d87f9e5fa49669dadd8" +checksum = "6af14725505314343e673e9ecb7cd7e8a36aa9791eb936235a3567cc31447ae4" dependencies = [ "itoa", "memchr", - "ryu", "serde", "serde_core", + "zmij", ] [[package]] @@ -4214,6 +4449,19 @@ version = "1.3.0" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "0fda2ff0d084019ba4d7c6f371c95d8fd75ce3524c3cb8fb653a3023f6323e64" +[[package]] +name = "simba" +version = "0.9.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "c99284beb21666094ba2b75bbceda012e610f5479dfcc2d6e2426f53197ffd95" +dependencies = [ + "approx", + "num-complex", + "num-traits", + "paste", + "wide", +] + [[package]] name = "simd-adler32" version = "0.3.8" @@ -4285,6 +4533,18 @@ dependencies = [ "serde", ] +[[package]] +name = "spade" +version = "2.15.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "fb313e1c8afee5b5647e00ee0fe6855e3d529eb863a0fdae1d60006c4d1e9990" +dependencies = [ + "hashbrown 0.15.5", + "num-traits", + "robust", + "smallvec", +] + [[package]] name = "spin" version = "0.9.8" @@ -4894,7 +5154,7 @@ checksum = "673a33c33048a5ade91a6b139580fa174e19fb0d23f396dca9fa15f2e1e49b35" dependencies = [ "cc", "downcast-rs 1.2.1", - "rustix 1.1.2", + "rustix 1.1.3", "scoped-tls", "smallvec", "wayland-sys", @@ -4907,7 +5167,7 @@ source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "c66a47e840dc20793f2264eb4b3e4ecb4b75d91c0dd4af04b456128e0bdd449d" dependencies = [ "bitflags 2.10.0", - "rustix 1.1.2", + "rustix 1.1.3", "wayland-backend", "wayland-scanner", ] @@ -4929,7 +5189,7 @@ version = "0.31.11" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "447ccc440a881271b19e9989f75726d60faa09b95b0200a9b7eb5cc47c3eeb29" dependencies = [ - "rustix 1.1.2", + "rustix 1.1.3", "wayland-client", "xcursor", ] @@ -5131,6 +5391,16 @@ dependencies = [ "web-sys", ] +[[package]] +name = "wide" +version = "0.7.33" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "0ce5da8ecb62bcd8ec8b7ea19f69a51275e91299be594ea5cc6ef7819e16cd03" +dependencies = [ + "bytemuck", + "safe_arch", +] + [[package]] name = "winapi" version = "0.3.9" @@ -5729,7 +5999,7 @@ dependencies = [ "libc", "libloading", "once_cell", - "rustix 1.1.2", + "rustix 1.1.3", "x11rb-protocol", ] @@ -5802,6 +6072,12 @@ dependencies = [ "syn", ] +[[package]] +name = "zmij" +version = "0.1.8" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "f1dccf46b25b205e4bebe1d5258a991df1cc17801017a845cb5b3fe0269781aa" + [[package]] name = "zune-core" version = "0.4.12" diff --git a/Cargo.toml b/Cargo.toml index 1033eadf..609f8c5e 100644 --- a/Cargo.toml +++ b/Cargo.toml @@ -6,6 +6,7 @@ license = "AGPL-3.0-only" rust-version = "1.88.0" [dependencies] +avian2d = "0.3" bevy = "0.16.0" bevy-inspector-egui = "0.32" diff --git a/src/birdoids/mod.rs b/src/birdoids/mod.rs index afd25e15..0430c386 100644 --- a/src/birdoids/mod.rs +++ b/src/birdoids/mod.rs @@ -1,5 +1,6 @@ pub mod physics; +use avian2d::prelude::*; use bevy::prelude::*; use bevy_spatial::{ AutomaticUpdate, SpatialAccess, SpatialStructure, TransformMode, kdtree::KDTree2, @@ -106,6 +107,8 @@ fn spawn_boids( Mesh2d(meshes.add(Circle::new(1.0))), MeshMaterial2d(materials.add(Color::srgb(1.0, 1.0, 1.0))), Transform::from_translation(vel * 20.0), + // RigidBody::Dynamic, + Collider::circle(1.0), )); } } diff --git a/src/debug_plugin.rs b/src/debug_plugin.rs index 43f60da0..2f774b24 100644 --- a/src/debug_plugin.rs +++ b/src/debug_plugin.rs @@ -1,8 +1,8 @@ +use avian2d::prelude::*; use bevy::{prelude::*, window::PrimaryWindow}; -use bevy_spatial::{SpatialAccess, kdtree::KDTree2}; use crate::birdoids::{ - Boid, TrackedByKdTree, center_of_boids, physics::Force, physics::Velocity, velocity_of_boids, + Boid, center_of_boids, physics::Force, physics::Velocity, velocity_of_boids, }; const SCANRADIUS: f32 = 50.0; @@ -109,7 +109,7 @@ fn update_scanner_mode( fn do_scan( boids_query: Query<(&Transform, &Velocity, &Force), With>, scanner_query: Query<(&Transform, &SelectionMode, &ScannerMode), With>, - spatial_tree: Res>, + spatial: SpatialQuery, /* Push info to summary somewhere */ mut gizmos: Gizmos, ) { @@ -117,24 +117,36 @@ fn do_scan( match select_mode { SelectionMode::NearestSingle => todo!(), SelectionMode::CircularArea => { - let boids = spatial_tree.within_distance(cursor_pos.translation.xy(), SCANRADIUS); + let boids = spatial.shape_hits( + &Collider::circle(SCANRADIUS), + cursor_pos.translation.xy(), + 0.0, + Dir2::Y, + 64, + &ShapeCastConfig::from_max_distance(100.0), + &SpatialQueryFilter::default() + ).into_iter() + .map(|shape_hit| { + let entt = shape_hit.entity; + let (tsfm, vel, _) = boids_query + .get(entt) + .expect("Debugger scanned a Boid missing one of it's components!"); + (tsfm, vel) + }); + match scan_mode { ScannerMode::CenterOfMass => { if let Some(center_mass) = center_of_boids( - // boids returns too many things. - // Map over it and extract only the Vec3's - boids.iter().map(|item| item.0), + // `center_of_boids` needs an Iterator, so we map over + // the output tuple to make one. + boids.map(|item| item.0.translation.xy()), ) { gizmos.circle_2d(center_mass, 1.0, bevy::color::palettes::css::RED); } } ScannerMode::Velocity => { - if let Some(avg_velocity) = velocity_of_boids(boids.iter().map(|item| { - let entity_id = item.1.unwrap_or_else(|| panic!("Entity has no ID!")); - let (_, vel, _) = boids_query - .get(entity_id) - .unwrap_or_else(|_| panic!("Boid has no Velocity component!")); - (*vel).xy() * 1.0 + if let Some(avg_velocity) = velocity_of_boids(boids.map(|item| { + (*item.1).xy() * 1.0 })) { // cursor_pos.translation is already in world space, so I can skip the window -> world transform like in update_cursor() gizmos.line_2d( diff --git a/src/main.rs b/src/main.rs index 4b8e4852..b6723cd2 100644 --- a/src/main.rs +++ b/src/main.rs @@ -1,3 +1,4 @@ +use avian2d::prelude::*; use bevy::prelude::*; mod birdoids; @@ -24,5 +25,6 @@ fn main() { .add_plugins(EguiPlugin::default()) .add_plugins(ResourceInspectorPlugin::::new()) // TODO: monitor only the flocking params resource (once it exists) .add_plugins(ResourceInspectorPlugin::::new()) + .add_plugins(PhysicsPlugins::default()) .run(); }