When event target frame is destroyed, `PresShell::NotifyDestroyingFrame` updates
current event target content to the frame content. However, event target of
some DOM events need to be `Element`. Therefore,
`PresShell::mCurrentEventTarget` needs to store at least the handling
`EventMessage` to consider whether the event target can be non-element content
node or only element node. So, we need to make `PresShell::EventTargetInfo`
store `EventMessage`. Then, we can make `PresShell::NotifyDestroyingFrame`
prefer inclusive ancestor element as new event target from the `EventMessage`.
Although I don't understand what's going on the reported case, but I found the
simple case when event target is changed to a `Text` with the assertion in
`PresShell::DispatchEventToDOM`. Therefore, this patch has a new test.
Note that if target frame is a frame for element, e.g., when event target is
a focused element, `IsForbiddenDispatchingToNonElementContent` result won't
change the behavior. Therefore, its implementation is not optimized for
non-user input events.
Differential Revision: https://phabricator.services.mozilla.com/D217205
`PresShell::mCurrentEventTargetContent` may be update to non-element node
when `PresShell::mCurrentEventTargetFrame` is destroyed. Therefore, for
avoiding it, I'd like to add `EventMessage` to the group to consider whether
the content needs to be `Element`. However, adding new members for current
and stack would make `PresShell` members more messy. Therefore, I'd like to
group the data with the simple struct.
Differential Revision: https://phabricator.services.mozilla.com/D217204
Before this patch, it could happen that `PresShell::GoToAnchor()` was called while loading a document.
This method did not know about text fragments before,
and would scroll the anchor (ie., the first text directive) to the top of the view.
This was noticeable for pages that took longer to load, where the text directive was scrolled to the center first, and then to the top.
This patch saves the desired vertical scroll position as a member in `PresShell` and makes `GoToAnchor()` scroll to the center as well.
Additionally, this patch updates the test file target document to make it more mobile-friendly.
Differential Revision: https://phabricator.services.mozilla.com/D216039
This patch makes some adjustments to follow the spec more strictly by
separating highlighting a text fragment (ie. adding the ranges to a `eTargetText` Selection)
from scrolling to it.
Scrolling to the text fragment now follows the steps given in [0] more closely,
in particular now the closest common ancestor of the target range is being used
as `:target` element.
This change also sets the focus to the start of the first text fragment, as indicated by the spec.
This resets the normal selection on the page.
The wpt test in /css/css-pseudo/target-text-005.html is based on the idea of having a same-doc
text fragment navigation with a selection.
This test fails with this patch applied, because the selection is reset.
It is currently unclear what behavior is correct here, thus the test is kept for now.
[0]: https://wicg.github.io/scroll-to-text-fragment/#invoking-text-directives
Differential Revision: https://phabricator.services.mozilla.com/D211025
This patch makes some adjustments to follow the spec more strictly by
separating highlighting a text fragment (ie. adding the ranges to a `eTargetText` Selection)
from scrolling to it.
Scrolling to the text fragment now follows the steps given in [0] more closely,
in particular now the closest common ancestor of the target range is being used
as `:target` element.
This change also sets the focus to the start of the first text fragment, as indicated by the spec.
This resets the normal selection on the page.
The wpt test in /css/css-pseudo/target-text-005.html is based on the idea of having a same-doc
text fragment navigation with a selection.
This test fails with this patch applied, because the selection is reset.
It is currently unclear what behavior is correct here, thus the test is kept for now.
[0]: https://wicg.github.io/scroll-to-text-fragment/#invoking-text-directives
Differential Revision: https://phabricator.services.mozilla.com/D211025
`eContextMenu` event may be fired from `widget`. Therefore, different from
`ePointerClick` and `ePointerAuxClick`, they may cross the process boundary,
may be handled by APZ and may be dispatched into the DOM after a delay.
Therefore, this patch is complicated than the previous patch. This adds
* New IPC message handlers for sending/receiving a `WidgetPointerEvent`
* New `DelayedPointerEvent` class and templated `MouseInput::ToWidgetEvent`
* `PresShell::EventHandler` handles `eContextMenu` as same as `WidgetMouseEvent`
Differential Revision: https://phabricator.services.mozilla.com/D213003
`PresShell::GetRootScrollFrameAsScrollable()` is equivalent to
`PresShell::GetRootScrollContainerFrame()`.
In ScrollContainerFrame.h, `DecideScrollableLayer()` has two versions, one has
four parameters, and the other has five parameters with the fifth parameter
`aDirtyRectHasBeenOverriden` having a default value `nullptr`. When we switch
the caller from `nsIScrollableFrame` to `ScrollContainerFrame`, we need to
remove the default value for the fifth parameter to avoid ambiguity.
Differential Revision: https://phabricator.services.mozilla.com/D211494
This patch starts from renaming `PresShell::GetScrollableFrameToScroll()` to
`PresShell::GetScrollContainerFrameToScroll()`, making it return
`ScrollContainerFrame*`, and then fixing other helpers until everything
compiles. As before, we can remove some `do_QueryFrame`.
Differential Revision: https://phabricator.services.mozilla.com/D211491
In theory, changing the return type from `nsIFrame*` to `ScrollContainerFrame*`
exposes `ScrollContainerFrame` to the callers who might not needed, but almost
all of the callers in cpp files are already exposed to `nsIScrollableFrame`, as
demonstrated in this patch via replacing the #include from
"nsIScrollableFrame.h" to "ScrollContainerFrame.h", so this is OK.
Some callers can be simplified since we no longer need `do_QueryFrame` to
`nsIScrollableFrame`.
Differential Revision: https://phabricator.services.mozilla.com/D211488
`PresShell::GetRootScrollFrameAsScrollable()` is equivalent to
`PresShell::GetRootScrollContainerFrame()`.
In ScrollContainerFrame.h, `DecideScrollableLayer()` has two versions, one has
four parameters, and the other has five parameters with the fifth parameter
`aDirtyRectHasBeenOverriden` having a default value `nullptr`. When we switch
the caller from `nsIScrollableFrame` to `ScrollContainerFrame`, we need to
remove the default value for the fifth parameter to avoid ambiguity.
Differential Revision: https://phabricator.services.mozilla.com/D211494
This patch starts from renaming `PresShell::GetScrollableFrameToScroll()` to
`PresShell::GetScrollContainerFrameToScroll()`, making it return
`ScrollContainerFrame*`, and then fixing other helpers until everything
compiles. As before, we can remove some `do_QueryFrame`.
Differential Revision: https://phabricator.services.mozilla.com/D211491
In theory, changing the return type from `nsIFrame*` to `ScrollContainerFrame*`
exposes `ScrollContainerFrame` to the callers who might not needed, but almost
all of the callers in cpp files are already exposed to `nsIScrollableFrame`, as
demonstrated in this patch via replacing the #include from
"nsIScrollableFrame.h" to "ScrollContainerFrame.h", so this is OK.
Some callers can be simplified since we no longer need `do_QueryFrame` to
`nsIScrollableFrame`.
Differential Revision: https://phabricator.services.mozilla.com/D211488
This telemetry was trying to measure three things:
* The time spent during style / layout in a tick. This is useful.
* The times SetNeed{Style,Layout} flush have been called. This is not a
particularly useful metric, there's not much to learn or change from
it. Any call is basically free as long as they're consecutive /
there's no flush in between.
* The number of times layout / style has been flushed during a tick.
This is more useful than the above but, similarly, there's not too
much to be learned here. Number of flushes can be completely
orthogonal to how expensive it has been.
It also had a number of flaws:
* It is recorded per-PresShell, so we get multiple pings per tick.
* Similarly, if a sub-frame dies before the tick, we just never report
that time.
Instead, refactor it to make it simpler, and just record the first
metric reliably. This simplifies the code substantially, and I don't
think we're losing much.
The histograms are also expired. We might want to renew this, I'll file
a follow-up to either properly renew this if we plan to look at it, or
remove the code entirely from the tree.
Differential Revision: https://phabricator.services.mozilla.com/D210907
In bug 1895870 I (somewhat unintentionally) made this code not called at
all.
Instead of scheduling a 30ms timer if reflow was interrupted, we just
schedule a reflow for the next refresh driver tick via
EnsureLayoutFlush(). Which is what would happen anyways before my change
in presence of other changes (like page loading appending content or
what not).
I think thus that the new behavior is more predictable (the 30ms timer
was never quite measured, it was introduced in bug 499447).
So, just simplify the code.
Differential Revision: https://phabricator.services.mozilla.com/D210890
We can just use `mFrameConstructor` to call `GetRootFrame()`. In order to do so
while keeping `PresShell::GetRootFrame()` as a inline method, we need to include
`nsCSSFrameConstructor` header in `PresShell.h`, and remove `PresShell` header
in `nsCSSFrameConstructor.h`. That means we can no longer inline
`RestyleManager()` since it needs to access `PresShell`, but it's OK since
`RestyleManager` is used only in the frame constructor, and is probably not in
the hot path.
Differential Revision: https://phabricator.services.mozilla.com/D210670
PresShell doesn't do anything different if it gets called with
FlushType::Display vs FlushType::Layout. It should be fine to just pass
FlushType::Layout where appropriate and remove the redundant check.
Differential Revision: https://phabricator.services.mozilla.com/D210274
There's no call to AddRefreshObserver(FlushType::Layout), so we don't
need to track layout flushes. The only reason we need
mLayoutFlushObservers is so that reflows triggered from the style flush
get processed. But at that point, we can just flush layout directly.
There's no really good distinction between style flushes and layout
flushes with container queries anyways, so this makes the code simpler
to reason about.
Differential Revision: https://phabricator.services.mozilla.com/D209924
This patch integrates the algorithm to find a text fragment range
into the document loading mechanism.
Unlike described in the spec, the fragment directive is not stripped
from the URL in the Session History Entry, instead it is stripped when
setting the URI into the Document using `Document::SetURI()`,
as well as when accessing the URL through `Location`.
The `PresShell` class is extended by a new method which sets the
ranges created from the text directives into the FrameSelection as
TargetText selection and scrolls it into view.
Security restrictions like force load at top and cross-origin iframes
are not yet considered in this patch.
Differential Revision: https://phabricator.services.mozilla.com/D195688
This patch integrates the algorithm to find a text fragment range
into the document loading mechanism.
Unlike described in the spec, the fragment directive is not stripped
from the URL in the Session History Entry, instead it is stripped when
setting the URI into the Document using `Document::SetURI()`,
as well as when accessing the URL through `Location`.
The `PresShell` class is extended by a new method which sets the
ranges created from the text directives into the FrameSelection as
TargetText selection and scrolls it into view.
Security restrictions like force load at top and cross-origin iframes
are not yet considered in this patch.
Differential Revision: https://phabricator.services.mozilla.com/D195688
This patch integrates the algorithm to find a text fragment range
into the document loading mechanism.
Unlike described in the spec, the fragment directive is not stripped
from the URL in the Session History Entry, instead it is stripped when
setting the URI into the Document using `Document::SetURI()`,
as well as when accessing the URL through `Location`.
The `PresShell` class is extended by a new method which sets the
ranges created from the text directives into the FrameSelection as
TargetText selection and scrolls it into view.
Security restrictions like force load at top and cross-origin iframes
are not yet considered in this patch.
Differential Revision: https://phabricator.services.mozilla.com/D195688
This patch integrates the algorithm to find a text fragment range
into the document loading mechanism.
Unlike described in the spec, the fragment directive is not stripped
from the URL in the Session History Entry, instead it is stripped when
setting the URI into the Document using `Document::SetURI()`,
as well as when accessing the URL through `Location`.
The `PresShell` class is extended by a new method which sets the
ranges created from the text directives into the FrameSelection as
TargetText selection and scrolls it into view.
Security restrictions like force load at top and cross-origin iframes
are not yet considered in this patch.
Differential Revision: https://phabricator.services.mozilla.com/D195688
The reason of the bug is, no `mouseup` event is fired after the `pointerup`
event listener removed the target. Therefore, `nsIFrame::HandleRelease()` does
not run and nobody cleans up the drag state of the `nsFrameSelection`.
This is caused by that `PresShell::EventHandler::DispatchPrecedingPointerEvent()`
updates only event target frame of the following mouse event target if the
pointer event target was removed from the tree, however, the frame may not be
ready. In this case, `PresShell::GetCurrentContent()` will clear both current
event target content and frame because its composed document (`nullptr`) never
matches with the document for the `PresShell`. Therefore, it needs to update
the target too.
This patch makes all developers won't create similar bugs, this encapsulate
`EventTargetData::mContent` and `EventTargetData::mFrame` to make their setters
clean up or automatically check the relation.
Differential Revision: https://phabricator.services.mozilla.com/D201053
`inert-iframe-hittest.html` expects that `:hover` state should be updated
immediately after a pointer down. The state is updated by
`EventStateManager::NotifyMouseOver` [1] when we received a real or synthetic
`eMouseMove`. Therefore, the hover state may have not set yet if no refresh
occurs between the pointer down and checking the result.
Additionally, some WPT for UI Events and Pointer Events expect that `mouseover`
or `mouseout` should be fired before `mouseup`/`pointerup` if a preceding
`mousedown` or `pointerdown` event listener removes the target. So, this
patch may fix intermittent failures of them if there are.
Therefore, we should flush pending synthetic `mousemove` event for keeping the
event order as same as they happen. However, simply flushing it causes
unexpected pointer capture state change because
`PointerEventHandler::ProcessPointerCaptureForMouse` handles synthetic
`mousemove` but it should not cause pointer boundary events at the moment (the
pointer boundary events should be fired when the pointer is actually moved, note
that this is different rule from the rules of mouse boundary events).
Therefore, this patch changes
`PointerEventHandler::ShouldGeneratePointerEventFromMouse`.
However, this blocks `lostpointercatpure` event when the capturing content has
already been removed from the DOM tree. The path is,
`EventHandler::HandleEventWithPointerCapturingContentWithoutItsFrame` stops
dispatching `pointerup` nor `pointercancel` in this case, but
`EventStateManager::PostHandleEvent` is the only handler of implicit pointer
capture release. Therefore, we need to make it dispatch lostpointercatpure`
event if the canceling event caused `ePointerUp` or `ePointerCancel`.
Finally, this patch fixes a bug of `browser_ext_browserAction_popup_preload.js`.
It tests the pre-loading which starts when `mouseover` before `mousedown` on a
widget. However, it does not correctly emulate the user input.
* Synthesizing only `mouseover` does not update the internal pointer info and
does not cause dispatching related events.
* Synthesizing `mousedown` without `mousemove` cause `mouseover` before
`mouseup` because at dispatching `mousedown`, `PresShell` stores the cursor [2]
and the mouse boundary events will be dispatched before `mouseup`.
`ext-browserAction.js` assumes the events are fired as this order,
`mouseover` -> `mousedown` -> `mouseup`, but this would not work if the
preceding `mousemove` of `mousedown` is not correctly fired. I'm not sure
whether `mousemove` is always fired before `mousedown` on any environments,
but it should be rare and it affects only this kind of tricky code. For now,
fixing this in the test side must be enough.
1. https://searchfox.org/mozilla-central/rev/9a5bf21ea2dd04946734658f67f83f62ca76b0fa/dom/events/EventStateManager.cpp#4874,4913-4914
2. https://searchfox.org/mozilla-central/rev/9a5bf21ea2dd04946734658f67f83f62ca76b0fa/layout/base/PresShell.cpp#6756
Differential Revision: https://phabricator.services.mozilla.com/D193870
Right now, we reconstruct frames in response to a change in the CSS
`contain` property or `content-visibility`. This patch tries to optimize
this a bit:
1. Updates involving style containment change continue to force a
reconstruction, due to the need to handle counters/quotes.
2. Updates involving paint/layout containment change only force a
reconstruction if it's needed to handle absolutely/fixed
positioned descendants or floats (for this one, see also bug 1874826).
3. Other containment changes will only force a reflow and repaint.
Per the CSS contain spec, layout, style and paint containments are
enabled for `content-visibility: hidden` and `content-visibility: auto`.
As a consequence, changing `content-visibility` between `hidden` and
`auto` values no longer requires reconstruction. Changing between these
values and `visible` may need a reconstruction although authors may
generally avoid that in practice by forcing `style` containment.
Differential Revision: https://phabricator.services.mozilla.com/D197043
These days, after bug 1853323, about:PreferenceStyleSheet is basically
just an empty sheet for most users. For the ones that isn't, it's either
slightly or completely broken (see below).
If we were to implement this today, we'd do it with privileged env()
variables or media queries, and add a bunch of tests for different
combinations, but I don't think it's worth the effort:
* There's no UI for any of these prefs.
* There are no tests for any of these prefs.
* browser.display.focus_ring_or_anything is not great, it's better
replaced by browser.display.show_focus_rings, which actually makes
the :focus-visible pseudo-class work. Otherwise the native controls
may show no rings even though this pref is set.
* for browser.display.focus_ring_style = 0, the color used
(-moz-mac-focusring) is not implemented in any non-macOS platform.
* The ::-moz-focus-inner rules are completely useless nowadays, because
::-moz-focus-inner only works on the windows native theme (which
isn't used on content).
* The focus colors are not color-scheme aware.
So given those, and that if you want the specific current behavior,
these are trivially implementable as a web extension (by using a user
stylesheet), I think we should just remove this code altogether.
Differential Revision: https://phabricator.services.mozilla.com/D190464