This works with margin and page-size, though we can't properly test mixed
page-size yet due to limitations in both print preview testing (which does not
handle multiple pages) and paged reftests (which ignore page-size).
It may be appropriate to remove the @page { margin } propagation from Servo
after this change.
Differential Revision: https://phabricator.services.mozilla.com/D158227
This works with margin and page-size, though we can't properly test mixed
page-size yet due to limitations in both print preview testing (which does not
handle multiple pages) and paged reftests (which ignore page-size).
It may be appropriate to remove the @page { margin } propagation from Servo
after this change.
Differential Revision: https://phabricator.services.mozilla.com/D158227
* Make non-menulist popups just absolute positioned top-layer items.
* Simplify menulist popups to just be static-positioned items under
nsMenuFrame.
We need to keep kPopupList only for nsMenuFrame. In the future it can be
removed, see TODO in xul.css
Differential Revision: https://phabricator.services.mozilla.com/D161404
* Make non-menulist popups just absolute positioned top-layer items.
* Simplify menulist popups to just be static-positioned items under
nsMenuFrame.
We need to keep kPopupList only for nsMenuFrame. In the future it can be
removed, see TODO in xul.css
Differential Revision: https://phabricator.services.mozilla.com/D161404
* Make non-menulist popups just absolute positioned top-layer items.
* Simplify menulist popups to just be static-positioned items under
nsMenuFrame.
We need to keep kPopupList only for nsMenuFrame. In the future it can be
removed, see TODO in xul.css
Differential Revision: https://phabricator.services.mozilla.com/D161404
* Make non-menulist popups just absolute positioned top-layer items.
* Simplify menulist popups to just be static-positioned items under
nsMenuFrame.
We need to keep kPopupList only for nsMenuFrame. In the future it can be
removed, see TODO in xul.css
Differential Revision: https://phabricator.services.mozilla.com/D161404
SetFrame() is equivalent to `operator=`, so external callers can use `operator=`
instead. For the two callers wanting to set `nsFrameList` to `AbsoluteFrameList`
in `nsCSSFrameConstructor`, removing SetFrame() disallows it. However, we can
easily change the declaration from `nsFrameList` to a `AbsoluteFrameList` to
resolve the problem.
Differential Revision: https://phabricator.services.mozilla.com/D160840
This patch doesn't change behavior.
AbsoluteFrameList is a derived class of nsFrameList, so we change it a move-only
class in order to nsFrameList move-only in Part 3.
Some detail of this patch:
- Define move constructor and move assignment operator for AbsoluteFrameList.
This effectively disables the auto generated copy constructor and copy
assignement operator.
- Initialize nsFrameConstructorSaveState's member variables in class definition,
and remove its constructor.
- Remove `mSavedFixedList` since we can rewire the logic in
`~nsFrameConstructorSaveState` and `PushAbsoluteContainingBlock()` to make it
redundant.
- Make self-assignment correct in nsFrameList's move assignment operator.
Differential Revision: https://phabricator.services.mozilla.com/D160014
This patch doesn't change behavior.
AbsoluteFrameList is a derived class of nsFrameList, so we change it a move-only
class in order to nsFrameList move-only in Part 3.
Some detail of this patch:
- Define move constructor and move assignment operator for AbsoluteFrameList.
This effectively disables the auto generated copy constructor and copy
assignement operator.
- Initialize nsFrameConstructorSaveState's member variables in class definition,
and remove its constructor.
- Remove `mSavedFixedList` since we can rewire the logic in
`~nsFrameConstructorSaveState` and `PushAbsoluteContainingBlock()` to make it
redundant.
- Make self-assignment correct in nsFrameList's move assignment operator.
Differential Revision: https://phabricator.services.mozilla.com/D160014
After this patch, we still need nsFrameList::Enumerator to iterate
nsFrameList::Slice. We might enhance nsFrameList::Iterator to support Slice, but
I'll leave this for another day.
Differential Revision: https://phabricator.services.mozilla.com/D158809
I feel it's hard to understand the purpose of ExtractHead(), especially where
aFrame is going after the call. Therefore, I rename it to TakeFramesBefore(),
and have it complement the existing RemoveFramesAfter(), which will be rename
later. No behavioral change intended.
Also, slightly reword the method's documentation to reflect the its new
name. (Remove the "sibling" wording from the comment since it's an
implementation details that frames are actually a doubly linked list.)
Differential Revision: https://phabricator.services.mozilla.com/D158806
This is a preparation to remove nsFrameList::FrameLinkEnumerator in the next
part.
FrameLinkEnumerator::Find() can be replaced with std::find/std::find_if.
Differential Revision: https://phabricator.services.mozilla.com/D158700
This applies both to the individual mStartPageValue and mEndPageValue fields
of the nsIFrame::PageValues struct, and for the nsIFrame::PageValuesProperty
being null to indicate both mStartPageValue and mEndPageValue are auto.
Fetching this is handled by nsIFrame::GetStartPageValue and
nsIFrame::GetEndPageValue, which also ensure the use of first-in-flow frames.
Differential Revision: https://phabricator.services.mozilla.com/D157873
After bug 1665476, it's pretty much a regular XUL box with a couple
special-cases that we can use IsRootElementStyle for. Do that, and allow
using nsFlexContainerFrame when using flexbox emulation.
Differential Revision: https://phabricator.services.mozilla.com/D158288
After bug 1665476, it's pretty much a regular XUL box with a couple
special-cases that we can use IsRootElementStyle for. Do that, and allow
using nsFlexContainerFrame when using flexbox emulation.
Differential Revision: https://phabricator.services.mozilla.com/D158288
After bug 1665476, it's pretty much a regular XUL box with a couple
special-cases that we can use IsRootElementStyle for. Do that, and allow
using nsFlexContainerFrame when using flexbox emulation.
Differential Revision: https://phabricator.services.mozilla.com/D158288
It's unused on mozilla-central, and Thunderbird can just use the canvas
frame as regular (X)HTML documents, so just use a canvas frame instead
of an nsRootBoxFrame for XUL as well.
nsRootBoxFrame was needed because of various XUL-specific things like
tooltips and so on lived there. But with the move away from XUL, that
functionality has been added to nsCanvasFrame already, behind a
principal check instead.
This also allows simplifying our background propagation setup, which was
only half-working for XUL documents (this bug is a consequence of that).
With this, most of the callers of nsCSSRendering::IsCanvasFrame can go.
They're only two of the frames that would return true for that that
actually paint backgrounds (nsCanvasFrame and nsRootBoxFrame), so the
codepaths in display list building and painting can just check
frame->IsCanvasFrame() instead.
The remaining caller to that function is
nsContainerFrame::SyncWindowProperties, and the change is also legit, in
the sense that the only thing SyncWindowProperties() really cares about
is propagating the max/min-width constraints from the root element's
style to the view/widget, and the only frame that would return true from
IsCanvasFrame and have a view is the viewport frame which is the root of
the frame tree.
Differential Revision: https://phabricator.services.mozilla.com/D90846
It's unused on mozilla-central, and Thunderbird can just use the canvas
frame as regular (X)HTML documents, so just use a canvas frame instead
of an nsRootBoxFrame for XUL as well.
nsRootBoxFrame was needed because of various XUL-specific things like
tooltips and so on lived there. But with the move away from XUL, that
functionality has been added to nsCanvasFrame already, behind a
principal check instead.
This also allows simplifying our background propagation setup, which was
only half-working for XUL documents (this bug is a consequence of that).
With this, most of the callers of nsCSSRendering::IsCanvasFrame can go.
They're only two of the frames that would return true for that that
actually paint backgrounds (nsCanvasFrame and nsRootBoxFrame), so the
codepaths in display list building and painting can just check
frame->IsCanvasFrame() instead.
The remaining caller to that function is
nsContainerFrame::SyncWindowProperties, and the change is also legit, in
the sense that the only thing SyncWindowProperties() really cares about
is propagating the max/min-width constraints from the root element's
style to the view/widget, and the only frame that would return true from
IsCanvasFrame and have a view is the viewport frame which is the root of
the frame tree.
Differential Revision: https://phabricator.services.mozilla.com/D90846
Gijs for front-end bits, layout for the new CSS properties and the
removal of nsDeckFrame / nsStackLayout, Jamie and Morgan for the a11y
changes.
As discussed in the bug, the main tricky part here is handling a11y
correctly. For <deck>, that's trivial (just use `visibility: hidden` to
hide the panels visually, while removing the unselected panels from the
a11y tree).
For <tabpanels> however we need to do something special. We do want to
hide stuff visually, but we want to preserve the contents in the a11y
tree.
For that, the easiest fix is introducing a new privileged CSS property
(-moz-subtree-hidden-only-visually), which takes care of not painting
the frame, but marks stuff offscreen in the accessibility tree. This is
not intended to be a property used widely.
Other than that, the changes are relatively straight-forward, though
some of the accessible/mac changes I could get a sanity-check on.
Differential Revision: https://phabricator.services.mozilla.com/D157875
Gijs for front-end bits, layout for the new CSS properties and the
removal of nsDeckFrame / nsStackLayout, Jamie and Morgan for the a11y
changes.
As discussed in the bug, the main tricky part here is handling a11y
correctly. For <deck>, that's trivial (just use `visibility: hidden` to
hide the panels visually, while removing the unselected panels from the
a11y tree).
For <tabpanels> however we need to do something special. We do want to
hide stuff visually, but we want to preserve the contents in the a11y
tree.
For that, the easiest fix is introducing a new privileged CSS property
(-moz-subtree-hidden-only-visually), which takes care of not painting
the frame, but marks stuff offscreen in the accessibility tree. This is
not intended to be a property used widely.
Other than that, the changes are relatively straight-forward, though
some of the accessible/mac changes I could get a sanity-check on.
Differential Revision: https://phabricator.services.mozilla.com/D157875
This also properly handles placeholder frames, and ensures that when checking
next/prev sibling we ignore placeholder frames.
To properly test this for multiple levels of page value propagation, we also
need to use FirstInFlow to get page values when checking for breaks in block
frames.
Differential Revision: https://phabricator.services.mozilla.com/D157175
Create XULButtonElement instead to do the event handling. Pretty much a
straight port, this allows these elements to respect CSS display
properly (and use modern flexbox rather than old XUL layout).
Differential Revision: https://phabricator.services.mozilla.com/D157509
The page-name property only applies to boxes which can create class A
breakpoints. One of the qualifiers for this is a block-level item, which is
the child of a block frame. Additionally, page-name propagation only occurs
through frames for which the page-name property applies, because where it does
not apply the auto page-name is propagated instead.
This means we only need to worry about block frames, and only use specified
page-name for BlockOutside frames.
Differential Revision: https://phabricator.services.mozilla.com/D155285
This also adds a small post-processing step for frame-construction to ensure
that replaced frames (or more generally frames with content but no children)
have the auto page-name set on them.
When page-name value tracking is switched to be lazy, this post-processing step
will likely be redundant and can be removed.
Differential Revision: https://phabricator.services.mozilla.com/D152701
The page-name property only applies to boxes which can create class A
breakpoints. One of the qualifiers for this is a block-level item, which is
the child of a block frame. Additionally, page-name propagation only occurs
through frames for which the page-name property applies, because where it does
not apply the auto page-name is propagated instead.
This means we only need to worry about block frames, and only use specified
page-name for BlockOutside frames.
Differential Revision: https://phabricator.services.mozilla.com/D155285
This also adds a small post-processing step for frame-construction to ensure
that replaced frames (or more generally frames with content but no children)
have the auto page-name set on them.
When page-name value tracking is switched to be lazy, this post-processing step
will likely be redundant and can be removed.
Differential Revision: https://phabricator.services.mozilla.com/D152701
I haven't spotted any UI regression from this, and this should generally
make the XUL -> modern flex transition easier, and simplify some
of the relevant code.
This does fix a few layout issues with emulated flexbox.
For the most part, this shouldn't change behavior without that. This
changes behavior if you have mixed inline/non-inline content in the same
XUL box (before they'd get a single item, now you'd get the flexbox /
grid behavior of one item per inline run), and multiple inline-elements
(which would become their own flex items). But I pushed a patch with
some asserts and they didn't fire on our browser mochitests, so I think
we're good.
The UA rule refactoring (removing the inherit from xul anon blocks)
shouldn't matter in practice, since we only have one item (so
box-ordinal is irrelevant) and they have overflow: visible (so
text-overflow and overflow-clip-box shouldn't have an effect).
Differential Revision: https://phabricator.services.mozilla.com/D156375
By making image loading in <embed> and <object> behave more like when
an <iframe> loads an image, we can make sure that the synthetic
document generated is process switched if the image is cross
origin. This is done by making image loading in nsObjectLoadingContent
follow the document loading path.
We also make sure that we pass the image size back to the embedder
element to not get stuck with the intrinsic size.
To avoid named targeting being able to target these synthetic
documents, as well as showing up in `Window.frames` and being counted
in `Window.length`, we keep a filtered list of non-synthetic browsing
contexts for that use-case.
This feature is controlled by two prefs:
* browser.opaqueResponseBlocking.syntheticBrowsingContext
This triggers the creation of synthetic documents for images loaded
in <object> or embed.
* browser.opaqueResponseBlocking.syntheticBrowsingContext.filter
This turns on the filtering of synthetic browsing contexts in named
targeting, `Window.length` and `Window.frames`.
Differential Revision: https://phabricator.services.mozilla.com/D148117
Instead, do this just before we addd the frame construction items, where CSS
break-after/break-before is handled.
This also fixes the expectations of three tests where our expectations have
changed. The test page-name-img-001 now succeeds with correct results because
of this change, though the other img and the canvas tests fail due issues with
fragmentation named pages and replaced frames.
The issues with replaced frames are currently caused because our page-break
logic occurs in nsCSSFrameConstructor::AddFrameConstructionItemsInternal, but
this is performed for the parent frame. As the replaced frames have no
children, we never process their children in
nsCSSFrameConstructor::AddFrameConstructionItemsInternal.
The issue with replaced frames will be fixed by
https://bugzilla.mozilla.org/1779645
Differential Revision: https://phabricator.services.mozilla.com/D151331
Add an implementation of CSS `contain: style`. This introduces two new
data structures, the ContainStyleScope and ContainStyleScopeManager.
ContainStyleScope manages one `contain: style` "world" which has its own
counter and quote lists. The contents of these lists depend on their
parent scopes, but are not affected by their children.
ContainStyleScopeManager manages a tree of scopes starting at a root
scope which is outside of any `contain: style` element.
Scopes are stored in a hash table that is keyed off of the nsIContent
which establishes the `contain: style` scope. When modifying quote or
content lists, the ContainStyleScopeManager is responsible for finding
the appropriate `contain: style` scope to modify.
Perhaps the most complex part of this is that counters and quotes have
read access to the state of counters and quotes that are in ancestor
`contain: style` scopes. In the case of counters, USE nodes that are at
the beginning of counter lists might have a counter scope that starts in
an ancestor `contain: style` scope. When nsCounterNode::SetScope() is
called, the code may look upward in the `contain: style` scope tree to
find the start of the counter scope. In the case of quotes, the first
node in the quote list must look for the state of quotes in ancestor
`contain: style` scopes.
Differential Revision: https://phabricator.services.mozilla.com/D149508
Add an implementation of CSS `contain: style`. This introduces two new
data structures, the ContainStyleScope and ContainStyleScopeManager.
ContainStyleScope manages one `contain: style` "world" which has its own
counter and quote lists. The contents of these lists depend on their
parent scopes, but are not affected by their children.
ContainStyleScopeManager manages a tree of scopes starting at a root
scope which is outside of any `contain: style` element.
Scopes are stored in a hash table that is keyed off of the nsIContent
which establishes the `contain: style` scope. When modifying quote or
content lists, the ContainStyleScopeManager is responsible for finding
the appropriate `contain: style` scope to modify.
Perhaps the most complex part of this is that counters and quotes have
read access to the state of counters and quotes that are in ancestor
`contain: style` scopes. In the case of counters, USE nodes that are at
the beginning of counter lists might have a counter scope that starts in
an ancestor `contain: style` scope. When nsCounterNode::SetScope() is
called, the code may look upward in the `contain: style` scope tree to
find the start of the counter scope. In the case of quotes, the first
node in the quote list must look for the state of quotes in ancestor
`contain: style` scopes.
Differential Revision: https://phabricator.services.mozilla.com/D149508
Add a dom/base/rust crate called just "dom" where we can share these.
Most of the changes are automatic:
s/mozilla::EventStates/mozilla::dom::ElementState/
s/EventStates/ElementState/
s/NS_EVENT_STATE_/ElementState::/
s/NS_DOCUMENT_STATE_/DocumentState::/
And so on. This requires a new cbindgen version to avoid ugly casts for
large shifts.
Differential Revision: https://phabricator.services.mozilla.com/D148537
Don't generate the button if the combobox doesn't need it anyways (if the
appearance is not menulist).
While at it improve the code that reframes on appearance: textfield changes so
that it only applies to number inputs as it should.
This shouldn't change behavior.
Differential Revision: https://phabricator.services.mozilla.com/D145712
This has a TODO about empty page names on previous sibling frames, to match
Chrome's behavior of page break coalescing we should be looking to the frame
before that sibling and check for page breaks there instead.
Differential Revision: https://phabricator.services.mozilla.com/D140423
This doesn't change behavior just yet, but seems worth doing separately.
With this patch, we can render content overlaid on top of an image
frame, by attaching a shadow root to it. The idea is to use this for
text recognition (OCR) of text inside images.
I chose to implement this using the DynamicLeaf stuff that I removed in
bug 1746310 (because nsMenuPopupFrame was its only user).
That seems simpler than either a new frame class, or more special cases
in the frame constructor, etc. But let me know if you disagree.
There are further changes that we want to do. For example, trying to
select the overlaid text with the mouse right now will start dragging
the image. For that, we might need to tweak our selection / mouse
dragging code. But those seem all changes that can go on top of this.
Differential Revision: https://phabricator.services.mozilla.com/D140638