Skip to content

Commit a657478

Browse files
jakobhellermannalice-i-cecileAlice Cecilemockersf
authored
resolve all internal ambiguities (#10411)
- ignore all ambiguities that are not a problem - remove `.before(Assets::<Image>::track_assets),` that points into a different schedule (-> should this be caught?) - add some explicit orderings: - run `poll_receivers` and `update_accessibility_nodes` after `window_closed` in `bevy_winit::accessibility` - run `bevy_ui::accessibility::calc_bounds` after `CameraUpdateSystem` - run ` bevy_text::update_text2d_layout` and `bevy_ui::text_system` after `font_atlas_set::remove_dropped_font_atlas_sets` - add `app.ignore_ambiguity(a, b)` function for cases where you want to ignore an ambiguity between two independent plugins `A` and `B` - add `IgnoreAmbiguitiesPlugin` in `DefaultPlugins` that allows cross-crate ambiguities like `bevy_animation`/`bevy_ui` - Fixes #9511 ## Before **Render** ![render_schedule_Render dot](https://github.com/bevyengine/bevy/assets/22177966/1c677968-7873-40cc-848c-91fca4c8e383) **PostUpdate** ![schedule_PostUpdate dot](https://github.com/bevyengine/bevy/assets/22177966/8fc61304-08d4-4533-8110-c04113a7367a) ## After **Render** ![render_schedule_Render dot](https://github.com/bevyengine/bevy/assets/22177966/462f3b28-cef7-4833-8619-1f5175983485) **PostUpdate** ![schedule_PostUpdate dot](https://github.com/bevyengine/bevy/assets/22177966/8cfb3d83-7842-4a84-9082-46177e1a6c70) --------- Co-authored-by: Alice Cecile <alice.i.cecile@gmail.com> Co-authored-by: Alice Cecile <alice.i.cecil@gmail.com> Co-authored-by: François <mockersf@gmail.com>
1 parent 13d3de8 commit a657478

File tree

19 files changed

+199
-28
lines changed

19 files changed

+199
-28
lines changed

crates/bevy_a11y/src/lib.rs

Lines changed: 2 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -105,6 +105,7 @@ impl Plugin for AccessibilityPlugin {
105105
fn build(&self, app: &mut bevy_app::App) {
106106
app.init_resource::<AccessibilityRequested>()
107107
.init_resource::<ManageAccessibilityUpdates>()
108-
.init_resource::<Focus>();
108+
.init_resource::<Focus>()
109+
.allow_ambiguous_component::<AccessibilityNode>();
109110
}
110111
}

crates/bevy_app/src/app.rs

Lines changed: 32 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -1000,6 +1000,38 @@ impl App {
10001000
self.world.allow_ambiguous_resource::<T>();
10011001
self
10021002
}
1003+
1004+
/// Suppress warnings and errors that would result from systems in these sets having ambiguities
1005+
/// (conflicting access but indeterminate order) with systems in `set`.
1006+
///
1007+
/// When possible, do this directly in the `.add_systems(Update, a.ambiguous_with(b))` call.
1008+
/// However, sometimes two independant plugins `A` and `B` are reported as ambiguous, which you
1009+
/// can only supress as the consumer of both.
1010+
#[track_caller]
1011+
pub fn ignore_ambiguity<M1, M2, S1, S2>(
1012+
&mut self,
1013+
schedule: impl ScheduleLabel,
1014+
a: S1,
1015+
b: S2,
1016+
) -> &mut Self
1017+
where
1018+
S1: IntoSystemSet<M1>,
1019+
S2: IntoSystemSet<M2>,
1020+
{
1021+
let schedule = schedule.intern();
1022+
let mut schedules = self.world.resource_mut::<Schedules>();
1023+
1024+
if let Some(schedule) = schedules.get_mut(schedule) {
1025+
let schedule: &mut Schedule = schedule;
1026+
schedule.ignore_ambiguity(a, b);
1027+
} else {
1028+
let mut new_schedule = Schedule::new(schedule);
1029+
new_schedule.ignore_ambiguity(a, b);
1030+
schedules.insert(new_schedule);
1031+
}
1032+
1033+
self
1034+
}
10031035
}
10041036

10051037
fn run_once(mut app: App) {

crates/bevy_audio/src/audio_output.rs

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -291,7 +291,7 @@ pub(crate) fn audio_output_available(audio_output: Res<AudioOutput>) -> bool {
291291

292292
/// Updates spatial audio sinks when emitter positions change.
293293
pub(crate) fn update_emitter_positions(
294-
mut emitters: Query<(&mut GlobalTransform, &SpatialAudioSink), Changed<GlobalTransform>>,
294+
mut emitters: Query<(&GlobalTransform, &SpatialAudioSink), Changed<GlobalTransform>>,
295295
spatial_scale: Res<SpatialScale>,
296296
) {
297297
for (transform, sink) in emitters.iter_mut() {

crates/bevy_core_pipeline/src/blit/mod.rs

Lines changed: 4 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -20,6 +20,10 @@ pub struct BlitPlugin;
2020
impl Plugin for BlitPlugin {
2121
fn build(&self, app: &mut App) {
2222
load_internal_asset!(app, BLIT_SHADER_HANDLE, "blit.wgsl", Shader::from_wgsl);
23+
24+
if let Ok(render_app) = app.get_sub_app_mut(RenderApp) {
25+
render_app.allow_ambiguous_resource::<SpecializedRenderPipelines<BlitPipeline>>();
26+
}
2327
}
2428

2529
fn finish(&self, app: &mut App) {

crates/bevy_ecs/src/schedule/schedule.rs

Lines changed: 31 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -244,6 +244,37 @@ impl Schedule {
244244
self
245245
}
246246

247+
/// Suppress warnings and errors that would result from systems in these sets having ambiguities
248+
/// (conflicting access but indeterminate order) with systems in `set`.
249+
#[track_caller]
250+
pub fn ignore_ambiguity<M1, M2, S1, S2>(&mut self, a: S1, b: S2) -> &mut Self
251+
where
252+
S1: IntoSystemSet<M1>,
253+
S2: IntoSystemSet<M2>,
254+
{
255+
let a = a.into_system_set();
256+
let b = b.into_system_set();
257+
258+
let Some(&a_id) = self.graph.system_set_ids.get(&a.intern()) else {
259+
panic!(
260+
"Could not mark system as ambiguous, `{:?}` was not found in the schedule.
261+
Did you try to call `ambiguous_with` before adding the system to the world?",
262+
a
263+
);
264+
};
265+
let Some(&b_id) = self.graph.system_set_ids.get(&b.intern()) else {
266+
panic!(
267+
"Could not mark system as ambiguous, `{:?}` was not found in the schedule.
268+
Did you try to call `ambiguous_with` before adding the system to the world?",
269+
b
270+
);
271+
};
272+
273+
self.graph.ambiguous_with.add_edge(a_id, b_id, ());
274+
275+
self
276+
}
277+
247278
/// Configures a collection of system sets in this schedule, adding them if they does not exist.
248279
#[track_caller]
249280
pub fn configure_sets(&mut self, sets: impl IntoSystemSetConfigs) -> &mut Self {

crates/bevy_gizmos/src/lib.rs

Lines changed: 12 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -15,6 +15,17 @@
1515
//!
1616
//! See the documentation on [`Gizmos`] for more examples.
1717
18+
/// Label for the the render systems handling the
19+
#[derive(SystemSet, Clone, Debug, Hash, PartialEq, Eq)]
20+
pub enum GizmoRenderSystem {
21+
/// Adds gizmos to the [`Transparent2d`](bevy_core_pipeline::core_2d::Transparent2d) render phase
22+
#[cfg(feature = "bevy_sprite")]
23+
QueueLineGizmos2d,
24+
/// Adds gizmos to the [`Transparent3d`](bevy_core_pipeline::core_3d::Transparent3d) render phase
25+
#[cfg(feature = "bevy_pbr")]
26+
QueueLineGizmos3d,
27+
}
28+
1829
pub mod arcs;
1930
pub mod arrows;
2031
pub mod circles;
@@ -40,7 +51,7 @@ use bevy_ecs::{
4051
entity::Entity,
4152
query::{ROQueryItem, Without},
4253
reflect::{ReflectComponent, ReflectResource},
43-
schedule::IntoSystemConfigs,
54+
schedule::{IntoSystemConfigs, SystemSet},
4455
system::{
4556
lifetimeless::{Read, SRes},
4657
Commands, Query, Res, ResMut, Resource, SystemParamItem,

crates/bevy_gizmos/src/pipeline_2d.rs

Lines changed: 7 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -1,5 +1,5 @@
11
use crate::{
2-
line_gizmo_vertex_buffer_layouts, DrawLineGizmo, GizmoConfig, LineGizmo,
2+
line_gizmo_vertex_buffer_layouts, DrawLineGizmo, GizmoConfig, GizmoRenderSystem, LineGizmo,
33
LineGizmoUniformBindgroupLayout, SetLineGizmoBindGroup, LINE_SHADER_HANDLE,
44
};
55
use bevy_app::{App, Plugin};
@@ -8,7 +8,7 @@ use bevy_core_pipeline::core_2d::Transparent2d;
88

99
use bevy_ecs::{
1010
prelude::Entity,
11-
schedule::IntoSystemConfigs,
11+
schedule::{IntoSystemConfigs, IntoSystemSetConfigs},
1212
system::{Query, Res, ResMut, Resource},
1313
world::{FromWorld, World},
1414
};
@@ -34,10 +34,14 @@ impl Plugin for LineGizmo2dPlugin {
3434
render_app
3535
.add_render_command::<Transparent2d, DrawLineGizmo2d>()
3636
.init_resource::<SpecializedRenderPipelines<LineGizmoPipeline>>()
37+
.configure_sets(
38+
Render,
39+
GizmoRenderSystem::QueueLineGizmos2d.in_set(RenderSet::Queue),
40+
)
3741
.add_systems(
3842
Render,
3943
queue_line_gizmos_2d
40-
.in_set(RenderSet::Queue)
44+
.in_set(GizmoRenderSystem::QueueLineGizmos2d)
4145
.after(prepare_assets::<LineGizmo>),
4246
);
4347
}

crates/bevy_gizmos/src/pipeline_3d.rs

Lines changed: 7 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -1,5 +1,5 @@
11
use crate::{
2-
line_gizmo_vertex_buffer_layouts, DrawLineGizmo, GizmoConfig, LineGizmo,
2+
line_gizmo_vertex_buffer_layouts, DrawLineGizmo, GizmoConfig, GizmoRenderSystem, LineGizmo,
33
LineGizmoUniformBindgroupLayout, SetLineGizmoBindGroup, LINE_SHADER_HANDLE,
44
};
55
use bevy_app::{App, Plugin};
@@ -12,7 +12,7 @@ use bevy_core_pipeline::{
1212
use bevy_ecs::{
1313
prelude::Entity,
1414
query::Has,
15-
schedule::IntoSystemConfigs,
15+
schedule::{IntoSystemConfigs, IntoSystemSetConfigs},
1616
system::{Query, Res, ResMut, Resource},
1717
world::{FromWorld, World},
1818
};
@@ -36,10 +36,14 @@ impl Plugin for LineGizmo3dPlugin {
3636
render_app
3737
.add_render_command::<Transparent3d, DrawLineGizmo3d>()
3838
.init_resource::<SpecializedRenderPipelines<LineGizmoPipeline>>()
39+
.configure_sets(
40+
Render,
41+
GizmoRenderSystem::QueueLineGizmos3d.in_set(RenderSet::Queue),
42+
)
3943
.add_systems(
4044
Render,
4145
queue_line_gizmos_3d
42-
.in_set(RenderSet::Queue)
46+
.in_set(GizmoRenderSystem::QueueLineGizmos3d)
4347
.after(prepare_assets::<LineGizmo>),
4448
);
4549
}

crates/bevy_internal/src/default_plugins.rs

Lines changed: 43 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1,4 +1,4 @@
1-
use bevy_app::{PluginGroup, PluginGroupBuilder};
1+
use bevy_app::{Plugin, PluginGroup, PluginGroupBuilder};
22

33
/// This plugin group will add all the default plugins for a *Bevy* application:
44
/// * [`LogPlugin`](crate::log::LogPlugin)
@@ -133,10 +133,52 @@ impl PluginGroup for DefaultPlugins {
133133
group = group.add(bevy_gizmos::GizmoPlugin);
134134
}
135135

136+
group = group.add(IgnoreAmbiguitiesPlugin);
137+
136138
group
137139
}
138140
}
139141

142+
struct IgnoreAmbiguitiesPlugin;
143+
144+
impl Plugin for IgnoreAmbiguitiesPlugin {
145+
#[allow(unused_variables)] // Variables are used depending on enabled features
146+
fn build(&self, app: &mut bevy_app::App) {
147+
// bevy_ui owns the Transform and cannot be animated
148+
#[cfg(all(feature = "bevy_animation", feature = "bevy_ui"))]
149+
app.ignore_ambiguity(
150+
bevy_app::PostUpdate,
151+
bevy_animation::animation_player,
152+
bevy_ui::ui_layout_system,
153+
);
154+
155+
#[cfg(feature = "bevy_render")]
156+
if let Ok(render_app) = app.get_sub_app_mut(bevy_render::RenderApp) {
157+
#[cfg(all(feature = "bevy_gizmos", feature = "bevy_sprite"))]
158+
{
159+
render_app.ignore_ambiguity(
160+
bevy_render::Render,
161+
bevy_gizmos::GizmoRenderSystem::QueueLineGizmos2d,
162+
bevy_sprite::queue_sprites,
163+
);
164+
render_app.ignore_ambiguity(
165+
bevy_render::Render,
166+
bevy_gizmos::GizmoRenderSystem::QueueLineGizmos2d,
167+
bevy_sprite::queue_material2d_meshes::<bevy_sprite::ColorMaterial>,
168+
);
169+
}
170+
#[cfg(all(feature = "bevy_gizmos", feature = "bevy_pbr"))]
171+
{
172+
render_app.ignore_ambiguity(
173+
bevy_render::Render,
174+
bevy_gizmos::GizmoRenderSystem::QueueLineGizmos3d,
175+
bevy_pbr::queue_material_meshes::<bevy_pbr::StandardMaterial>,
176+
);
177+
}
178+
}
179+
}
180+
}
181+
140182
/// This plugin group will add the minimal plugins for a *Bevy* application:
141183
/// * [`TaskPoolPlugin`](crate::core::TaskPoolPlugin)
142184
/// * [`TypeRegistrationPlugin`](crate::core::TypeRegistrationPlugin)

crates/bevy_pbr/src/lib.rs

Lines changed: 9 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -361,6 +361,15 @@ impl Plugin for PbrPlugin {
361361
draw_3d_graph::node::SHADOW_PASS,
362362
bevy_core_pipeline::core_3d::graph::node::START_MAIN_PASS,
363363
);
364+
365+
render_app.ignore_ambiguity(
366+
bevy_render::Render,
367+
bevy_core_pipeline::core_3d::prepare_core_3d_transmission_textures,
368+
bevy_render::batching::batch_and_prepare_render_phase::<
369+
bevy_core_pipeline::core_3d::Transmissive3d,
370+
MeshPipeline,
371+
>,
372+
);
364373
}
365374

366375
fn finish(&self, app: &mut App) {

0 commit comments

Comments
 (0)