
# Objective - Fixes #19627 - Tackles part of #19644 - Supersedes #19629 - `Window` has become a very very very big component - As such, our change detection does not *really* work on it, as e.g. moving the mouse will cause a change for the entire window - We circumvented this with a cache - But, some things *shouldn't* be cached as they can be changed from outside the user's control, notably the cursor grab mode on web - So, we need to disable the cache for that - But because change detection is broken, that would result in the cursor grab mode being set every frame the mouse is moved - That is usually *not* what a dev wants, as it forces the cursor to be locked even when the end-user is trying to free the cursor on the browser - the cache in this situation is invalid due to #8949 ## Solution - Split `Window` into multiple components, each with working change detection - Disable caching of the cursor grab mode - This will only attempt to force the grab mode when the `CursorOptions` were touched by the user, which is *much* rarer than simply moving the mouse. - If this PR is merged, I'll do the exact same for the other constituents of `Window` as a follow-up ## Testing - Ran all the changed examples
45 lines
1.2 KiB
Markdown
45 lines
1.2 KiB
Markdown
---
|
|
title: Window is now split into multiple components
|
|
pull_requests: [19668]
|
|
---
|
|
|
|
`Window` has become a very large component over the last few releases. To improve our internal handling of it and to make it more approachable, we
|
|
have split it into multiple components, all on the same entity. So far, this affects `CursorOptions`:
|
|
|
|
```rust
|
|
// old
|
|
fn lock_cursor(primary_window: Single<&mut Window, With<PrimaryWindow>>) {
|
|
primary_window.cursor_options.grab_mode = CursorGrabMode::Locked;
|
|
}
|
|
|
|
// new
|
|
fn lock_cursor(primary_cursor_options: Single<&mut CursorOptions, With<PrimaryWindow>>) {
|
|
primary_cursor_options.grab_mode = CursorGrabMode::Locked;
|
|
}
|
|
```
|
|
|
|
This split also applies when specifying the initial settings for the primary window:
|
|
|
|
```rust
|
|
// old
|
|
app.add_plugins(DefaultPlugins.set(WindowPlugin {
|
|
primary_window: Some(Window {
|
|
cursor_options: CursorOptions {
|
|
grab_mode: CursorGrabMode::Locked,
|
|
..default()
|
|
},
|
|
..default()
|
|
}),
|
|
..default()
|
|
}));
|
|
|
|
// new
|
|
app.add_plugins(DefaultPlugins.set(WindowPlugin {
|
|
primary_cursor_options: Some(CursorOptions {
|
|
grab_mode: CursorGrabMode::Locked,
|
|
..default()
|
|
}),
|
|
..default()
|
|
}));
|
|
```
|