dependencies: Upgrade to WebRender 0.64 (#31486)

This brings the version of WebRender used in Servo up-to-date with Gecko
upstream. The big change here is that HiDPI is no longer handled via
WebRender. Instead this happens via a scale applied to the root layer in
the compositor. In addition to this change, various changes are made to
Servo to adapt to the new WebRender API.

Co-authored-by: Mukilan Thiyagarajan <mukilan@igalia.com>
This commit is contained in:
Martin Robinson 2024-03-14 18:40:54 +01:00 committed by GitHub
parent 4597aeae5f
commit ad37a54f59
No known key found for this signature in database
GPG key ID: B5690EEEBB952194
102 changed files with 704 additions and 600 deletions

View file

@ -12,7 +12,7 @@ use gfx::text::glyph::GlyphStore;
use gfx_traits::WebRenderEpochToU16;
use msg::constellation_msg::BrowsingContextId;
use net_traits::image_cache::UsePlaceholder;
use script_traits::compositor::{CompositorDisplayListInfo, ScrollTreeNodeId};
use script_traits::compositor::{CompositorDisplayListInfo, ScrollSensitivity, ScrollTreeNodeId};
use servo_geometry::MaxRect;
use style::color::{AbsoluteColor, ColorSpace};
use style::computed_values::text_decoration_style::T as ComputedTextDecorationStyle;
@ -23,9 +23,8 @@ use style::values::computed::{BorderStyle, Color, Length, LengthPercentage, Outl
use style::values::specified::text::TextDecorationLine;
use style::values::specified::ui::CursorKind;
use style_traits::CSSPixel;
use webrender_api::{self as wr, units, ClipChainId, ClipId, CommonItemProperties};
use webrender_api::{self as wr, units, BoxShadowClipMode, ClipChainId};
use wr::units::LayoutVector2D;
use wr::{BoxShadowClipMode, ScrollSensitivity};
use crate::context::LayoutContext;
use crate::display_list::conversions::ToWebRender;
@ -69,6 +68,11 @@ pub struct DisplayList {
/// data structure that the compositor uses to map hit tests to information
/// about the item hit.
pub compositor_info: CompositorDisplayListInfo,
/// A count of the number of SpatialTree nodes pushed to the WebRender display
/// list. This is merely to ensure that the currently-unused SpatialTreeItemKey
/// produced for every SpatialTree node is unique.
pub spatial_tree_count: u64,
}
impl DisplayList {
@ -90,8 +94,25 @@ impl DisplayList {
epoch,
root_scroll_sensitivity,
),
spatial_tree_count: 0,
}
}
pub fn define_clip_chain<I>(&mut self, parent: ClipChainId, clips: I) -> ClipChainId
where
I: IntoIterator<Item = wr::ClipId>,
I::IntoIter: ExactSizeIterator + Clone,
{
// WebRender has two different ways of expressing "no clip." ClipChainId::INVALID should be
// used for primitives, but `None` is used for stacking contexts and clip chains. We convert
// to the `Option<ClipChainId>` representation here. Just passing Some(ClipChainId::INVALID)
// leads to a crash.
let parent = match parent {
ClipChainId::INVALID => None,
parent => Some(parent),
};
self.wr.define_clip_chain(parent, clips)
}
}
pub(crate) struct DisplayListBuilder<'a> {
@ -139,7 +160,7 @@ impl DisplayList {
) -> (FnvHashMap<BrowsingContextId, Size2D<f32, CSSPixel>>, bool) {
let mut builder = DisplayListBuilder {
current_scroll_node_id: self.compositor_info.root_reference_frame_id,
current_clip_chain_id: ClipChainId(0, self.compositor_info.pipeline_id),
current_clip_chain_id: ClipChainId::INVALID,
element_for_canvas_background: fragment_tree.canvas_background.from_element,
is_contentful: false,
context,
@ -167,7 +188,7 @@ impl<'a> DisplayListBuilder<'a> {
wr::CommonItemProperties {
clip_rect,
spatial_id: self.current_scroll_node_id.spatial_id,
clip_id: ClipId::ClipChain(self.current_clip_chain_id),
clip_chain_id: self.current_clip_chain_id,
flags: style.get_webrender_primitive_flags(),
}
}
@ -268,7 +289,7 @@ impl Fragment {
common.clip_rect,
&wr::SpaceAndClipInfo {
spatial_id: common.spatial_id,
clip_id: common.clip_id,
clip_chain_id: common.clip_chain_id,
},
iframe.pipeline_id.to_webrender(),
true,
@ -304,12 +325,10 @@ impl Fragment {
let clip_chain_id = builder.current_clip_chain_id;
let spatial_id = builder.current_scroll_node_id.spatial_id;
builder.wr().push_hit_test(
&CommonItemProperties {
clip_rect: rect.to_webrender(),
clip_id: ClipId::ClipChain(clip_chain_id),
spatial_id,
flags: style.get_webrender_primitive_flags(),
},
rect.to_webrender(),
clip_chain_id,
spatial_id,
style.get_webrender_primitive_flags(),
hit_info,
);
}
@ -405,7 +424,7 @@ impl Fragment {
color: &AbsoluteColor,
) {
let rect = rect.to_webrender();
let wavy_line_thickness = (0.33 * rect.size.height).ceil();
let wavy_line_thickness = (0.33 * rect.size().height).ceil();
let text_decoration_color = fragment
.parent_style
.clone_text_decoration_color()
@ -452,8 +471,8 @@ impl<'a> BuilderForBoxFragment<'a> {
};
let corner = |corner: &style::values::computed::BorderCornerRadius| {
Size2D::new(
resolve(&corner.0.width.0, border_rect.size.width),
resolve(&corner.0.height.0, border_rect.size.height),
resolve(&corner.0.width.0, border_rect.size().width),
resolve(&corner.0.height.0, border_rect.size().height),
)
};
let b = fragment.style.get_border();
@ -577,9 +596,15 @@ impl<'a> BuilderForBoxFragment<'a> {
let mut common = builder.common_properties(self.border_rect, &self.fragment.style);
if let Some(clip_chain_id) = self.border_edge_clip(builder) {
common.clip_id = ClipId::ClipChain(clip_chain_id);
common.clip_chain_id = clip_chain_id;
}
builder.wr().push_hit_test(&common, hit_info);
builder.wr().push_hit_test(
common.clip_rect,
common.clip_chain_id,
common.spatial_id,
common.flags,
hit_info,
);
}
fn build_background_for_painter(
@ -1011,13 +1036,10 @@ fn clip_for_radii(
if radii.is_zero() {
None
} else {
let clip_chain_id = builder.current_clip_chain_id;
let parent_space_and_clip = wr::SpaceAndClipInfo {
spatial_id: builder.current_scroll_node_id.spatial_id,
clip_id: ClipId::ClipChain(clip_chain_id),
};
let spatial_id = builder.current_scroll_node_id.spatial_id;
let parent_clip_chain_id = builder.current_clip_chain_id;
let new_clip_id = builder.wr().define_clip_rounded_rect(
&parent_space_and_clip,
spatial_id,
wr::ComplexClipRegion {
rect,
radii,
@ -1026,8 +1048,8 @@ fn clip_for_radii(
);
Some(
builder
.wr()
.define_clip_chain(Some(clip_chain_id), [new_clip_id]),
.display_list
.define_clip_chain(parent_clip_chain_id, [new_clip_id]),
)
}
}