compositing: Support per-Painter operations and message handling (#40788)

Currently, only the first `Painter` is used for all operations in the
`Compositor`. This change modifies the compositor API and message
handling to allow routing the operations to the correct `Painter` via a
provided `PainterId` or `WebViewId`.

This change is to enable support for per-`WebView`s `RenderingContext`s.

Testing: This change shouldn't change behavior, so existing WPT tests
should cover it.

---------

Signed-off-by: Mukilan Thiyagarajan <mukilan@igalia.com>
Signed-off-by: Martin Robinson <mrobinson@igalia.com>
Co-authored-by: Martin Robinson <mrobinson@igalia.com>
This commit is contained in:
Mukilan Thiyagarajan
2025-11-21 18:45:55 +05:30
committed by GitHub
parent 9c4db3b7d1
commit 90595e3570
13 changed files with 238 additions and 136 deletions

View File

@@ -9,6 +9,7 @@ use std::sync::{Arc, Mutex, Weak};
use std::time::{Duration, Instant};
use std::{f64, mem};
use base::id::WebViewId;
use compositing_traits::{CrossProcessCompositorApi, ImageUpdate, SerializableImageData};
use content_security_policy::sandboxing_directive::SandboxingFlagSet;
use dom_struct::dom_struct;
@@ -165,6 +166,7 @@ impl FrameHolder {
#[derive(MallocSizeOf)]
pub(crate) struct MediaFrameRenderer {
webview_id: WebViewId,
player_id: Option<usize>,
glplayer_id: Option<u64>,
compositor_api: CrossProcessCompositorApi,
@@ -179,8 +181,13 @@ pub(crate) struct MediaFrameRenderer {
}
impl MediaFrameRenderer {
fn new(compositor_api: CrossProcessCompositorApi, player_context: WindowGLContext) -> Self {
fn new(
webview_id: WebViewId,
compositor_api: CrossProcessCompositorApi,
player_context: WindowGLContext,
) -> Self {
Self {
webview_id,
player_id: None,
glplayer_id: None,
compositor_api,
@@ -286,7 +293,8 @@ impl MediaFrameRenderer {
}
if !updates.is_empty() {
self.compositor_api.update_images(updates);
self.compositor_api
.update_images(self.webview_id.into(), updates);
}
}
@@ -351,7 +359,10 @@ impl VideoFrameRenderer for MediaFrameRenderer {
Some(current_frame) => {
self.old_frame = Some(current_frame.image_key);
let Some(new_image_key) = self.compositor_api.generate_image_key_blocking() else {
let Some(new_image_key) = self
.compositor_api
.generate_image_key_blocking(self.webview_id)
else {
return;
};
@@ -384,7 +395,10 @@ impl VideoFrameRenderer for MediaFrameRenderer {
updates.push(ImageUpdate::AddImage(new_image_key, descriptor, image_data));
},
None => {
let Some(image_key) = self.compositor_api.generate_image_key_blocking() else {
let Some(image_key) = self
.compositor_api
.generate_image_key_blocking(self.webview_id)
else {
return;
};
@@ -416,7 +430,8 @@ impl VideoFrameRenderer for MediaFrameRenderer {
updates.push(ImageUpdate::AddImage(image_key, descriptor, image_data));
},
}
self.compositor_api.update_images(updates);
self.compositor_api
.update_images(self.webview_id.into(), updates);
}
}
@@ -624,6 +639,7 @@ impl HTMLMediaElement {
in_flight_play_promises_queue: Default::default(),
player: Default::default(),
video_renderer: Arc::new(Mutex::new(MediaFrameRenderer::new(
document.webview_id(),
document.window().compositor_api().clone(),
document.window().get_player_context(),
))),