Skip to content

Fix fit_canvas_to_parent#11278

Merged
alice-i-cecile merged 3 commits intobevyengine:mainfrom
ThierryBerger:fix-fit_canvas_to_parent
Mar 3, 2024
Merged

Fix fit_canvas_to_parent#11278
alice-i-cecile merged 3 commits intobevyengine:mainfrom
ThierryBerger:fix-fit_canvas_to_parent

Conversation

@ThierryBerger
Copy link
Copy Markdown
Member

@ThierryBerger ThierryBerger commented Jan 9, 2024

Follow up to #11057

Implemented suggestions from reviewers from: a simpler fit_canvas_to_parent leads to an explicit CSS setting to the canvas.

From my understanding, it has do be set after wgpu creation due to wgpu overriding the canvas width/height: https://github.com/gfx-rs/wgpu/blob/4400a5847080d1164bdca93a90622414963ed9f3/examples/src/utils.rs#L68-L74

Changelog

  • Re-enable a fit_canvas_to_parent, it's removal from Remove CanvasParentResizePlugin #11057 was problematic. Still, its inner working is more simple than before: bevy doesn't handle its resizing, winit does.

Migration Guide

@ThierryBerger ThierryBerger changed the title Follow up to #11057 ; fix fit_canvas_to_parent Fix fit_canvas_to_parent Jan 9, 2024
@ThierryBerger ThierryBerger added C-Bug An unexpected or incorrect behavior A-Windowing Platform-agnostic interface layer to run your app in labels Jan 9, 2024
@alice-i-cecile alice-i-cecile added the O-Web Specific to web (WASM) builds label Jan 9, 2024
@alice-i-cecile alice-i-cecile added this to the 0.13 milestone Jan 9, 2024
@ThierryBerger ThierryBerger force-pushed the fix-fit_canvas_to_parent branch from c37cb7e to f0dd8b1 Compare January 9, 2024 22:48
Comment on lines +196 to +213
/// **Warning**: this will not behave as expected for parents that set their size according to the size of their
/// children. This creates a "feedback loop" that will result in the canvas growing on each resize. When using this
/// feature, ensure the parent's size is not affected by its children.
Copy link
Copy Markdown
Member Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I'm not too sure if this comment is still 100% correct

Comment on lines +93 to +100
let canvas: HtmlCanvasElement = web_sys::window()
.unwrap()
.document()
.unwrap()
.query_selector(&format!("canvas[data-raw-handle=\"{}\"]", handle.id))
.unwrap()
.unwrap()
.unchecked_into();
Copy link
Copy Markdown
Member Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Fortunately you don't need this whole block (and the corresponding crate features in web-sys), you can just use WindowExtWebSys::canvas(), which only needs one unwrap() that checks if you are on the main thread, which Bevy always is.

+ fit_canvas_to_parent: true,
prevent_default_event_handling: true,
- canvas: None,
+ canvas: Some("#bevy".to_string()),
Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

This will also not be needed if you use WindowExtWebSys::canvas().

Copy link
Copy Markdown
Member Author

@ThierryBerger ThierryBerger Jan 10, 2024

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Thanks for the insight!

You may be right about this specific example, but I think it's still ok to use that as a recommended way to use bevy, so the ability to target a specific canvas is in bevy user space opposed to the lower level winit functions.

Copy link
Copy Markdown
Member Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

For clarity, this "canvas" selector allows to declare the canvas at a specific place rather than relying on winit creating it

@ThierryBerger ThierryBerger force-pushed the fix-fit_canvas_to_parent branch 3 times, most recently from 2a0b14e to f168ae0 Compare January 10, 2024 09:25
Comment on lines +19 to +21
// Tells wasm to resize the window according to the available canvas
fit_canvas_to_parent: true,
Copy link
Copy Markdown
Member Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Suggested change
// Tells wasm to resize the window according to the available canvas
fit_canvas_to_parent: true,
// Tells wasm to set the CSS width and height properties to 100% for the target canvas.
// This can be useful to support window resizing.
fit_canvas_to_parent: true,

Maybe an improvement ?

@ThierryBerger ThierryBerger mentioned this pull request Jan 10, 2024
23 tasks
@tim-blackbird
Copy link
Copy Markdown
Contributor

tim-blackbird commented Jan 10, 2024

From my understanding, it has do be set after wgpu creation due to wgpu overriding the canvas width/height: gfx-rs/wgpu@4400a58/examples/src/utils.rs#L68-L74

No, wgpu only sets the html attributes width and height which are different from width and height inside the style attribute.
It's winit that overrides the style attribute's width and height whenever you request a resolution so this PR won't work.

I'd strongly prefer it if we could avoid having either winit or bevy modify the canvas style at all. That way, styling on the web page would just work without having to use !important.

edit: Commenting out the calls to with_inner_size stops winit from overriding the html styling.

@ThierryBerger
Copy link
Copy Markdown
Member Author

ThierryBerger commented Jan 10, 2024

I tested this PR and it works on my machine ™️ (firefox/windows):

This PR

image

On main

image

Thanks for correcting me on my assumption that wgpu sets the CSS! I want to believe you're right and winit does it, still I'm not sure where ?
The code you linked is from an example, so although related to our analysis, it's not the root cause of the CSS change on main.

It's winit that overrides the style attribute's width and height whenever you request a resolution

Does it override the style ? I don't think that's the case since winit 0.29, from this PR, when I resize the window, only the canvas attribute width/height changes, not the style.

I'm not sure resizing is what you were referring to with "request a resolution", maybe scale factor is a risk too ?

If you mean user explicitly using API to set the resolution, I think it's intentional enough a user wouldn't be surprised the CSS is "modified" (but still could use docs, and support to set it to % rather than pixels).

In other case, if CSS gets overridden implicitly after window creation, isn't it a bug 🤔 ? I think it shouldn't even be modified during window creation but I'm not sure.

@daxpedda
Copy link
Copy Markdown
Contributor

Winit doesn't touch width and height CSS properties unless you tell it to, e.g. WindowBuilder::with_inner_size() and Window::request_inner_size(). Even WindowEvent::ScaleFactorChanged doesn't do anything unless you actually modify the inner_size_writer. Everything else would be a bug.

Please let me know if Winit has any issue on that front, but from what I'm reading it seems to work correctly.

@tim-blackbird
Copy link
Copy Markdown
Contributor

winit is only adding the style attributes when explicitly requested in my testing, so that's all good.

If you mean user explicitly using API to set the resolution, I think it's intentional enough a user wouldn't be surprised the CSS is "modified" (but still could use docs, and support to set it to % rather than pixels.

Yes, that's what I was referring to. Allowing the resolution to be a percentage sounds like a better alternative to fit_canvas_to_parent, but that would still always override user styling on the page.

@ThierryBerger
Copy link
Copy Markdown
Member Author

Thanks for the precision!

So our culprit is https://github.com/Vrixyz/bevy/blob/f168ae0451e693232591e0b72ddb78726dfcb22c/crates/bevy_winit/src/winit_windows.rs#L85 ; not too far from my change.

There's a bunch of called to Window::request_inner_size() which we might want to audit to see if we need to apply that CSS change 🤔, not sure of their behaviour in wasm:

No bug within winit from my understanding so far :)

@alice-i-cecile alice-i-cecile removed this from the 0.13 milestone Jan 24, 2024
@hymm hymm added this to the 0.14 milestone Feb 11, 2024
@NiklasEi NiklasEi added the S-Ready-For-Final-Review This PR has been approved by the community. It's ready for a maintainer to consider merging it label Feb 29, 2024
@alice-i-cecile
Copy link
Copy Markdown
Member

@Vrixyz can you resolve merge conflicts so I can merge this in?

@ThierryBerger
Copy link
Copy Markdown
Member Author

I can do that ~sunday

@ThierryBerger ThierryBerger force-pushed the fix-fit_canvas_to_parent branch from f168ae0 to 106b8d3 Compare March 3, 2024 13:59
@alice-i-cecile alice-i-cecile added this pull request to the merge queue Mar 3, 2024
Merged via the queue into bevyengine:main with commit 8cf5fbb Mar 3, 2024
spectria-limina pushed a commit to spectria-limina/bevy that referenced this pull request Mar 9, 2024
Follow up to bevyengine#11057

Implemented suggestions from reviewers from: a simpler
fit_canvas_to_parent leads to an explicit CSS setting to the canvas.

From my understanding, it has do be set after wgpu creation due to wgpu
overriding the canvas width/height:
https://github.com/gfx-rs/wgpu/blob/4400a5847080d1164bdca93a90622414963ed9f3/examples/src/utils.rs#L68-L74


# Changelog

- Re-enable a `fit_canvas_to_parent`, it's removal from
bevyengine#11057 was problematic. Still,
its inner working is more simple than before: bevy doesn't handle its
resizing, winit does.

## Migration Guide

- Cancels the migration from
bevyengine#11057
v-kat pushed a commit to v-kat/bevy that referenced this pull request Mar 17, 2024
Follow up to bevyengine#11057

Implemented suggestions from reviewers from: a simpler
fit_canvas_to_parent leads to an explicit CSS setting to the canvas.

From my understanding, it has do be set after wgpu creation due to wgpu
overriding the canvas width/height:
https://github.com/gfx-rs/wgpu/blob/4400a5847080d1164bdca93a90622414963ed9f3/examples/src/utils.rs#L68-L74


# Changelog

- Re-enable a `fit_canvas_to_parent`, it's removal from
bevyengine#11057 was problematic. Still,
its inner working is more simple than before: bevy doesn't handle its
resizing, winit does.

## Migration Guide

- Cancels the migration from
bevyengine#11057
v-kat pushed a commit to v-kat/bevy that referenced this pull request Mar 21, 2024
Follow up to bevyengine#11057

Implemented suggestions from reviewers from: a simpler
fit_canvas_to_parent leads to an explicit CSS setting to the canvas.

From my understanding, it has do be set after wgpu creation due to wgpu
overriding the canvas width/height:
https://github.com/gfx-rs/wgpu/blob/4400a5847080d1164bdca93a90622414963ed9f3/examples/src/utils.rs#L68-L74


# Changelog

- Re-enable a `fit_canvas_to_parent`, it's removal from
bevyengine#11057 was problematic. Still,
its inner working is more simple than before: bevy doesn't handle its
resizing, winit does.

## Migration Guide

- Cancels the migration from
bevyengine#11057
v-kat pushed a commit to v-kat/bevy that referenced this pull request Apr 26, 2024
Follow up to bevyengine#11057

Implemented suggestions from reviewers from: a simpler
fit_canvas_to_parent leads to an explicit CSS setting to the canvas.

From my understanding, it has do be set after wgpu creation due to wgpu
overriding the canvas width/height:
https://github.com/gfx-rs/wgpu/blob/4400a5847080d1164bdca93a90622414963ed9f3/examples/src/utils.rs#L68-L74


# Changelog

- Re-enable a `fit_canvas_to_parent`, it's removal from
bevyengine#11057 was problematic. Still,
its inner working is more simple than before: bevy doesn't handle its
resizing, winit does.

## Migration Guide

- Cancels the migration from
bevyengine#11057
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

A-Windowing Platform-agnostic interface layer to run your app in C-Bug An unexpected or incorrect behavior O-Web Specific to web (WASM) builds S-Ready-For-Final-Review This PR has been approved by the community. It's ready for a maintainer to consider merging it

Projects

None yet

Development

Successfully merging this pull request may close these issues.

6 participants