Bug 258907 - REGRESSION(265043@main): Fullscreen mode only shows video in some part of the screen on Twitter
Summary: REGRESSION(265043@main): Fullscreen mode only shows video in some part of the...
Status: RESOLVED FIXED
Alias: None
Product: WebKit
Classification: Unclassified
Component: Media (show other bugs)
Version: WebKit Nightly Build
Hardware: Unspecified Unspecified
: P2 Normal
Assignee: zalan
URL:
Keywords: InRadar
Depends on:
Blocks:
 
Reported: 2023-07-05 17:20 PDT by Tim Nguyen (:ntim)
Modified: 2023-07-26 14:28 PDT (History)
7 users (show)

See Also:


Attachments
Patch (5.96 KB, patch)
2023-07-19 21:29 PDT, zalan
no flags Details | Formatted Diff | Diff
Patch (6.00 KB, patch)
2023-07-19 21:33 PDT, zalan
no flags Details | Formatted Diff | Diff
Patch (8.85 KB, patch)
2023-07-20 10:55 PDT, zalan
no flags Details | Formatted Diff | Diff
Patch (12.35 KB, patch)
2023-07-25 17:35 PDT, zalan
no flags Details | Formatted Diff | Diff
Patch (9.77 KB, patch)
2023-07-25 19:49 PDT, zalan
no flags Details | Formatted Diff | Diff

Note You need to log in before you can comment on or make changes to this bug.
Description Tim Nguyen (:ntim) 2023-07-05 17:20:04 PDT
rdar://111095697
Comment 1 Tim Nguyen (:ntim) 2023-07-05 17:44:03 PDT
Pull request: https://github.com/WebKit/WebKit/pull/15583
Comment 2 Tim Nguyen (:ntim) 2023-07-10 04:09:15 PDT
Pull request: https://github.com/WebKit/WebKit/pull/15689
Comment 3 zalan 2023-07-19 21:29:05 PDT
Created attachment 467077 [details]
Patch
Comment 4 zalan 2023-07-19 21:33:31 PDT
Created attachment 467078 [details]
Patch
Comment 5 Tim Nguyen (:ntim) 2023-07-19 22:23:57 PDT
Comment on attachment 467078 [details]
Patch

View in context: https://bugs.webkit.org/attachment.cgi?id=467078&action=review

> Source/WebCore/dom/FullscreenManager.cpp:478
> +    RenderBlock::removePositionedObject(downcast<RenderBox>(*renderer));

Note that it's possible that the block is just static before the top layer change (if someone sets `position: static !important;` on a dialog/popover).

Not sure if this needs to be guarded conditionally or not, but just mentioning it in case it does.

> Source/WebCore/dom/FullscreenManager.cpp:541
>          ancestor->addToTopLayer();

We probably want to do this `markRendererDirtyAfterTopLayerChange` logic for all ancestor documents, since when going fullscreen, the ancestor iframe(s) are getting pushed to the top layer as well, so this set up could have the same bug:

<div style="width: 500px; height: 500px; will-change: transform">
  <iframe src="document-that-calls-request-fullscreen.html" style="container-type: size">
</div>
Comment 6 Tim Nguyen (:ntim) 2023-07-19 22:26:58 PDT
Comment on attachment 467078 [details]
Patch

View in context: https://bugs.webkit.org/attachment.cgi?id=467078&action=review

>> Source/WebCore/dom/FullscreenManager.cpp:541
>>          ancestor->addToTopLayer();
> 
> We probably want to do this `markRendererDirtyAfterTopLayerChange` logic for all ancestor documents, since when going fullscreen, the ancestor iframe(s) are getting pushed to the top layer as well, so this set up could have the same bug:
> 
> <div style="width: 500px; height: 500px; will-change: transform">
>   <iframe src="document-that-calls-request-fullscreen.html" style="container-type: size">
> </div>

(So I think the `markRendererDirtyAfterTopLayerChange`  logic should either be in `addToTopLayer()` or the for loop)
Comment 7 zalan 2023-07-20 07:25:15 PDT
(In reply to Tim Nguyen (:ntim) from comment #5)
> Comment on attachment 467078 [details]
> Patch
> 
> View in context:
> https://bugs.webkit.org/attachment.cgi?id=467078&action=review
> 
> > Source/WebCore/dom/FullscreenManager.cpp:478
> > +    RenderBlock::removePositionedObject(downcast<RenderBox>(*renderer));
> 
> Note that it's possible that the block is just static before the top layer
> change (if someone sets `position: static !important;` on a dialog/popover).
At this point we are _after_ the style update and from layout perspective, whether or not the author says "static !important", it is still an out-of-flow box and is treated accordingly (see render tree dumps)
Comment 8 Tim Nguyen (:ntim) 2023-07-20 07:51:31 PDT
(In reply to zalan from comment #7)
> (In reply to Tim Nguyen (:ntim) from comment #5)
> > Comment on attachment 467078 [details]
> > Patch
> > 
> > View in context:
> > https://bugs.webkit.org/attachment.cgi?id=467078&action=review
> > 
> > > Source/WebCore/dom/FullscreenManager.cpp:478
> > > +    RenderBlock::removePositionedObject(downcast<RenderBox>(*renderer));
> > 
> > Note that it's possible that the block is just static before the top layer
> > change (if someone sets `position: static !important;` on a dialog/popover).
> At this point we are _after_ the style update and from layout perspective,
> whether or not the author says "static !important", it is still an
> out-of-flow box and is treated accordingly (see render tree dumps)

In the fullscreen case yes, because of the UA stylesheet forces everything with the fullscreen flag to `position: fixed !important`, but not necessarily dialog/popover (but I guess you're not handling them here so it doesn't matter too much).
Comment 9 Simon Fraser (smfr) 2023-07-20 09:15:23 PDT
Comment on attachment 467078 [details]
Patch

View in context: https://bugs.webkit.org/attachment.cgi?id=467078&action=review

> Source/WebCore/dom/FullscreenManager.cpp:476
> +    ASSERT(renderer->isFixedPositioned());

Can't a top layer element also be position:absolute?
Comment 10 zalan 2023-07-20 09:28:39 PDT
(In reply to Simon Fraser (smfr) from comment #9)
> Comment on attachment 467078 [details]
> Patch
> 
> View in context:
> https://bugs.webkit.org/attachment.cgi?id=467078&action=review
> 
> > Source/WebCore/dom/FullscreenManager.cpp:476
> > +    ASSERT(renderer->isFixedPositioned());
> 
> Can't a top layer element also be position:absolute?
No, not at this point.
Comment 11 zalan 2023-07-20 10:55:35 PDT
Created attachment 467081 [details]
Patch
Comment 12 zalan 2023-07-20 10:57:04 PDT
> We probably want to do this `markRendererDirtyAfterTopLayerChange` logic for
> all ancestor documents
That's a good point. I didn't know subframe could initiate fullscreen all the way to the top.
Comment 13 zalan 2023-07-20 10:58:30 PDT
(In reply to zalan from comment #12)
> > We probably want to do this `markRendererDirtyAfterTopLayerChange` logic for
> > all ancestor documents
> That's a good point. I didn't know subframe could initiate fullscreen all
> the way to the top.
I haven't managed yet to put such test case together though. iframes work fine when testing manually but for some reason they don't return the correct size when running layout test.
Comment 14 Tim Nguyen (:ntim) 2023-07-20 23:00:22 PDT
Comment on attachment 467081 [details]
Patch

View in context: https://bugs.webkit.org/attachment.cgi?id=467081&action=review

I can try to help with the fullscreen testcase

> Source/WebCore/dom/FullscreenManager.cpp:532
> +        auto containingBlockBeforeStyleUpdate = WeakPtr<RenderBlock> { };

setFullscreenFlag(true) will apply the :fullscreen pseudo  class styles, so "BeforeStyleUpdate" is vague here.
Comment 15 zalan 2023-07-21 06:15:07 PDT
(In reply to Tim Nguyen (:ntim) from comment #14)
> Comment on attachment 467081 [details]
> Patch
> 
> View in context:
> https://bugs.webkit.org/attachment.cgi?id=467081&action=review
> 
> I can try to help with the fullscreen testcase
> 
> > Source/WebCore/dom/FullscreenManager.cpp:532
> > +        auto containingBlockBeforeStyleUpdate = WeakPtr<RenderBlock> { };
> 
> setFullscreenFlag(true) will apply the :fullscreen pseudo  class styles, so
> "BeforeStyleUpdate" is vague here.
please suggest a better name!
Comment 16 Tim Nguyen (:ntim) 2023-07-24 10:34:59 PDT
(In reply to zalan from comment #15)
> (In reply to Tim Nguyen (:ntim) from comment #14)
> > Comment on attachment 467081 [details]
> > Patch
> > 
> > View in context:
> > https://bugs.webkit.org/attachment.cgi?id=467081&action=review
> > 
> > I can try to help with the fullscreen testcase
> > 
> > > Source/WebCore/dom/FullscreenManager.cpp:532
> > > +        auto containingBlockBeforeStyleUpdate = WeakPtr<RenderBlock> { };
> > 
> > setFullscreenFlag(true) will apply the :fullscreen pseudo  class styles, so
> > "BeforeStyleUpdate" is vague here.
> please suggest a better name!

Accurate names could be:
- containingBlockBeforeStyleResolution
- containingBlockAfterFullscreenStyleChanges

oldContainingBlock would be fine too.

BeforeStyleUpdate is ambiguous.
Comment 17 Tim Nguyen (:ntim) 2023-07-24 13:27:28 PDT
Comment on attachment 467081 [details]
Patch

r=me with the var rename + the extra testcase
Comment 18 Tim Nguyen (:ntim) 2023-07-24 13:27:43 PDT
r=me with the var rename + the extra testcase
Comment 19 Tim Nguyen (:ntim) 2023-07-24 13:28:58 PDT
Comment on attachment 467081 [details]
Patch

View in context: https://bugs.webkit.org/attachment.cgi?id=467081&action=review

> LayoutTests/fullscreen/fullscreen-containing-block-change.html:14
> +            <div style="position: absolute; left: 0; right: 0; top: 100px; bottom: 0; background-color: greenyellow;"></div>

optional, but we could assert the width of this descendant too.
Comment 20 zalan 2023-07-25 10:51:47 PDT
I am going to discuss this with Simon before landing.
Comment 21 Simon Fraser (smfr) 2023-07-25 16:20:07 PDT
Comment on attachment 467081 [details]
Patch

View in context: https://bugs.webkit.org/attachment.cgi?id=467081&action=review

> Source/WebCore/dom/FullscreenManager.cpp:475
> +    // Let's carry out the same set of tasks we would normally do when containg block changes for out-of-flow content.

"containg". Can this comment mention the other location this is called?

> Source/WebCore/dom/FullscreenManager.cpp:530
>          ancestor->setFullscreenFlag(true);

Other code uses a Style::PseudoClassChangeInvalidation. Should we do that here?

> Source/WebCore/dom/FullscreenManager.cpp:534
> +            containingBlockBeforeStyleUpdate = renderer->containingBlock();

Should grab this before setFullscreenFlag(true)

> Source/WebCore/dom/FullscreenManager.cpp:543
> +        markRendererDirtyAfterTopLayerChange(ancestor->renderer(), containingBlockBeforeStyleUpdate.get());

Do we need the same fix in HTMLElement::showPopover() and HTMLDialogElement::showModal()?
Comment 22 zalan 2023-07-25 17:35:27 PDT
Created attachment 467119 [details]
Patch
Comment 23 zalan 2023-07-25 19:49:48 PDT
Created attachment 467121 [details]
Patch
Comment 24 zalan 2023-07-25 19:52:34 PDT
> r=me with the var rename + the extra testcase
Had to remove the iframe test case. It was flaky timeout on both of my machines (and that's inline with what I experienced while I was trying to put a test case together)
Comment 25 zalan 2023-07-25 19:58:13 PDT
> Other code uses a Style::PseudoClassChangeInvalidation. Should we do that
> here?
Maybe? That's a question for Tim.

> Do we need the same fix in HTMLElement::showPopover() and
> HTMLDialogElement::showModal()?
Probably yes, but also we should figure out a better fix to replace this manual handling.
Comment 26 EWS 2023-07-25 20:32:34 PDT
Committed 266309@main (f82dc74981d8): <https://commits.webkit.org/266309@main>

All reviewed patches have been landed. Closing bug and clearing flags on attachment 467121 [details].
Comment 27 Tim Nguyen (:ntim) 2023-07-25 21:53:57 PDT
(In reply to zalan from comment #25)
> > Other code uses a Style::PseudoClassChangeInvalidation. Should we do that
> > here?
> Maybe? That's a question for Tim.

setFullscreenFlag() already uses `Style::PseudoClassChangeInvalidation`, but it's not sufficient, which is why we use `resolveStyle()` (though ideally, we should find out why exactly that is needed and replace it).

> > Do we need the same fix in HTMLElement::showPopover() and
> > HTMLDialogElement::showModal()?
> Probably yes, but also we should figure out a better fix to replace this
> manual handling.

In showPopover and showModal, we don't resolveStyle() in between adding the styles and adding to the top layer, so this fix isn't needed.
Comment 28 zalan 2023-07-26 08:39:58 PDT
(In reply to Tim Nguyen (:ntim) from comment #27)
> (In reply to zalan from comment #25)
> > > Other code uses a Style::PseudoClassChangeInvalidation. Should we do that
> > > here?
> > Maybe? That's a question for Tim.
> 
> setFullscreenFlag() already uses `Style::PseudoClassChangeInvalidation`, but
> it's not sufficient, which is why we use `resolveStyle()` (though ideally,
> we should find out why exactly that is needed and replace it).
> 
> > > Do we need the same fix in HTMLElement::showPopover() and
> > > HTMLDialogElement::showModal()?
> > Probably yes, but also we should figure out a better fix to replace this
> > manual handling.
> 
> In showPopover and showModal, we don't resolveStyle() in between adding the
> styles and adding to the top layer, so this fix isn't needed.
Sure, on trunk, but this approach is not future proof (i.e. we should not need to do any kind of manual dirty bit setting at this level)
Comment 29 Tim Nguyen (:ntim) 2023-07-26 08:44:36 PDT
(In reply to zalan from comment #28)
> (In reply to Tim Nguyen (:ntim) from comment #27)
> > (In reply to zalan from comment #25)
> > > > Other code uses a Style::PseudoClassChangeInvalidation. Should we do that
> > > > here?
> > > Maybe? That's a question for Tim.
> > 
> > setFullscreenFlag() already uses `Style::PseudoClassChangeInvalidation`, but
> > it's not sufficient, which is why we use `resolveStyle()` (though ideally,
> > we should find out why exactly that is needed and replace it).
> > 
> > > > Do we need the same fix in HTMLElement::showPopover() and
> > > > HTMLDialogElement::showModal()?
> > > Probably yes, but also we should figure out a better fix to replace this
> > > manual handling.
> > 
> > In showPopover and showModal, we don't resolveStyle() in between adding the
> > styles and adding to the top layer, so this fix isn't needed.
> Sure, on trunk, but this approach is not future proof (i.e. we should not
> need to do any kind of manual dirty bit setting at this level)

At some point, we'll probably want to rework top layer rendering to be a CSS property, so we can support transitions and other things. I suspect that this will replace this fix.
Comment 30 Simon Fraser (smfr) 2023-07-26 11:29:37 PDT
(In reply to Tim Nguyen (:ntim) from comment #27)
> In showPopover and showModal, we don't resolveStyle() in between adding the
> styles and adding to the top layer, so this fix isn't needed.

Right, but why do we need to resolveStyle in the fullscreen case?
Comment 31 Tim Nguyen (:ntim) 2023-07-26 14:28:55 PDT
(In reply to Simon Fraser (smfr) from comment #30)
> (In reply to Tim Nguyen (:ntim) from comment #27)
> > In showPopover and showModal, we don't resolveStyle() in between adding the
> > styles and adding to the top layer, so this fix isn't needed.
> 
> Right, but why do we need to resolveStyle in the fullscreen case?

Needs more investigation, but this predates the new fullscreen API fwiw.

If I remove it, I recall a bunch of assertions on fullscreen tests.