{"record":{"id":"309bdaa05cbc493b","repo":"bevyengine/bevy","slug":"point-cloud-must-contain-at-least-one-point-for-aa","errorCode":null,"errorMessage":"point cloud must contain at least one point for Aabb2d construction","messagePattern":"point cloud must contain at least one point for Aabb2d construction","errorType":"panic","errorClass":null,"httpStatus":null,"severity":"error","filePath":"crates/bevy_math/src/bounding/bounded2d/mod.rs","lineNumber":83,"sourceCode":"        }\n    }\n\n    /// Computes the smallest [`Aabb2d`] containing the given set of points,\n    /// transformed by the rotation and translation of the given isometry.\n    ///\n    /// # Panics\n    ///\n    /// Panics if the given set of points is empty.\n    #[inline]\n    pub fn from_point_cloud(isometry: impl Into<Isometry2d>, points: &[Vec2]) -> Aabb2d {\n        let isometry = isometry.into();\n\n        // Transform all points by rotation\n        let mut iter = points.iter().map(|point| isometry.rotation * *point);\n\n        let first = iter\n            .next()\n            .expect(\"point cloud must contain at least one point for Aabb2d construction\");\n\n        let (min, max) = iter.fold((first, first), |(prev_min, prev_max), point| {\n            (point.min(prev_min), point.max(prev_max))\n        });\n\n        Aabb2d {\n            min: min + isometry.translation,\n            max: max + isometry.translation,\n        }\n    }\n\n    /// Computes the smallest [`BoundingCircle`] containing this [`Aabb2d`].\n    #[inline]\n    pub fn bounding_circle(&self) -> BoundingCircle {\n        let radius = self.min.distance(self.max) / 2.0;\n        BoundingCircle::new(self.center(), radius)\n    }\n","sourceCodeStart":65,"sourceCodeEnd":101,"githubUrl":"https://github.com/bevyengine/bevy/blob/396ca727080776bd313bb892423b7d94e03b81b4/crates/bevy_math/src/bounding/bounded2d/mod.rs#L65-L101","documentation":"Aabb2d::from_point_cloud panics via .expect when the point slice is empty (crates/bevy_math/src/bounding/bounded2d/mod.rs:83) — the min/max fold needs a first point to seed from. This is a panic, not a Result: callers must filter empty inputs before invoking it.","triggerScenarios":"Calling Aabb2d::from_point_cloud(isometry, &[]) — an empty vertex set, empty collider points, or a collection sampled before any data arrived.","commonSituations":"Computing bounds for empty meshes during loading; physics colliders built from filtered geometry that matched nothing; procedural generation edge cases with zero points.","solutions":["Check points is non-empty before calling from_point_cloud.","Skip or early-return for empty point sets instead of computing bounds.","Log where point clouds are produced to find the component emitting empty sets."],"exampleFix":"// before\nlet aabb = Aabb2d::from_point_cloud(iso, &points); // panics on empty slice\n\n// after\nif points.is_empty() {\n    return; // nothing to bound\n}\nlet aabb = Aabb2d::from_point_cloud(iso, &points);","handlingStrategy":"validation","validationCode":"fn point_cloud_aabb2d(iso: impl Into<Isometry2d>, points: &[Vec2]) -> Option<Aabb2d> {\n    if points.is_empty() {\n        return None;\n    }\n    Some(Aabb2d::from_point_cloud(iso, points))\n}","typeGuard":null,"tryCatchPattern":null,"preventionTips":["Never call from_point_cloud on a slice you have not length-checked.","Skip bounds computation for empty meshes/colliders during loading.","Return Option<Aabb2d> from your own bounds helpers to force callers to handle empty."],"tags":["bevy","math","bounding-volume","aabb","panic","empty-slice"],"backgroundTag":"empty-slice-panic","analyzedSha":"396ca727080776bd313bb892423b7d94e03b81b4","analyzedAt":"2026-08-20T16:12:39.808Z","contentChangedAt":"2026-08-20T16:12:39.808Z","schemaVersion":2},"datasetVersion":"2026-09-14T05:17:10.506Z"}