Skip to main content

browser_protocol/headlessexperimental/
mod.rs

1//! This domain provides experimental commands only supported in headless mode.
2
3
4use serde::{Serialize, Deserialize};
5use serde_json::Value as JsonValue;
6use std::borrow::Cow;
7
8/// Encoding options for a screenshot.
9
10#[derive(Debug, Clone, Serialize, Deserialize, Default)]
11#[serde(rename_all = "camelCase")]
12pub struct ScreenshotParams<'a> {
13    /// Image compression format (defaults to png).
14    #[serde(skip_serializing_if = "Option::is_none")]
15    format: Option<Cow<'a, str>>,
16    /// Compression quality from range [0..100] (jpeg and webp only).
17    #[serde(skip_serializing_if = "Option::is_none")]
18    quality: Option<i64>,
19    /// Optimize image encoding for speed, not for resulting size (defaults to false)
20    #[serde(skip_serializing_if = "Option::is_none")]
21    optimizeForSpeed: Option<bool>,
22}
23
24impl<'a> ScreenshotParams<'a> {
25    pub fn builder() -> ScreenshotParamsBuilder<'a> {
26        ScreenshotParamsBuilder {
27            format: None,
28            quality: None,
29            optimizeForSpeed: None,
30        }
31    }
32    pub fn format(&self) -> Option<&str> { self.format.as_deref() }
33    pub fn quality(&self) -> Option<i64> { self.quality }
34    pub fn optimizeForSpeed(&self) -> Option<bool> { self.optimizeForSpeed }
35}
36
37#[derive(Default)]
38pub struct ScreenshotParamsBuilder<'a> {
39    format: Option<Cow<'a, str>>,
40    quality: Option<i64>,
41    optimizeForSpeed: Option<bool>,
42}
43
44impl<'a> ScreenshotParamsBuilder<'a> {
45    /// Image compression format (defaults to png).
46    pub fn format(mut self, format: impl Into<Cow<'a, str>>) -> Self { self.format = Some(format.into()); self }
47    /// Compression quality from range [0..100] (jpeg and webp only).
48    pub fn quality(mut self, quality: i64) -> Self { self.quality = Some(quality); self }
49    /// Optimize image encoding for speed, not for resulting size (defaults to false)
50    pub fn optimizeForSpeed(mut self, optimizeForSpeed: bool) -> Self { self.optimizeForSpeed = Some(optimizeForSpeed); self }
51    pub fn build(self) -> ScreenshotParams<'a> {
52        ScreenshotParams {
53            format: self.format,
54            quality: self.quality,
55            optimizeForSpeed: self.optimizeForSpeed,
56        }
57    }
58}
59
60/// Sends a BeginFrame to the target and returns when the frame was completed. Optionally captures a
61/// screenshot from the resulting frame. Requires that the target was created with enabled
62/// BeginFrameControl. Designed for use with --run-all-compositor-stages-before-draw, see also
63/// https://goo.gle/chrome-headless-rendering for more background.
64
65#[derive(Debug, Clone, Serialize, Deserialize, Default)]
66#[serde(rename_all = "camelCase")]
67pub struct BeginFrameParams<'a> {
68    /// Timestamp of this BeginFrame in Renderer TimeTicks (milliseconds of uptime). If not set,
69    /// the current time will be used.
70    #[serde(skip_serializing_if = "Option::is_none")]
71    frameTimeTicks: Option<f64>,
72    /// The interval between BeginFrames that is reported to the compositor, in milliseconds.
73    /// Defaults to a 60 frames/second interval, i.e. about 16.666 milliseconds.
74    #[serde(skip_serializing_if = "Option::is_none")]
75    interval: Option<f64>,
76    /// Whether updates should not be committed and drawn onto the display. False by default. If
77    /// true, only side effects of the BeginFrame will be run, such as layout and animations, but
78    /// any visual updates may not be visible on the display or in screenshots.
79    #[serde(skip_serializing_if = "Option::is_none")]
80    noDisplayUpdates: Option<bool>,
81    /// If set, a screenshot of the frame will be captured and returned in the response. Otherwise,
82    /// no screenshot will be captured. Note that capturing a screenshot can fail, for example,
83    /// during renderer initialization. In such a case, no screenshot data will be returned.
84    #[serde(skip_serializing_if = "Option::is_none")]
85    screenshot: Option<ScreenshotParams<'a>>,
86}
87
88impl<'a> BeginFrameParams<'a> {
89    pub fn builder() -> BeginFrameParamsBuilder<'a> {
90        BeginFrameParamsBuilder {
91            frameTimeTicks: None,
92            interval: None,
93            noDisplayUpdates: None,
94            screenshot: None,
95        }
96    }
97    pub fn frameTimeTicks(&self) -> Option<f64> { self.frameTimeTicks }
98    pub fn interval(&self) -> Option<f64> { self.interval }
99    pub fn noDisplayUpdates(&self) -> Option<bool> { self.noDisplayUpdates }
100    pub fn screenshot(&self) -> Option<&ScreenshotParams<'a>> { self.screenshot.as_ref() }
101}
102
103#[derive(Default)]
104pub struct BeginFrameParamsBuilder<'a> {
105    frameTimeTicks: Option<f64>,
106    interval: Option<f64>,
107    noDisplayUpdates: Option<bool>,
108    screenshot: Option<ScreenshotParams<'a>>,
109}
110
111impl<'a> BeginFrameParamsBuilder<'a> {
112    /// Timestamp of this BeginFrame in Renderer TimeTicks (milliseconds of uptime). If not set,
113    /// the current time will be used.
114    pub fn frameTimeTicks(mut self, frameTimeTicks: f64) -> Self { self.frameTimeTicks = Some(frameTimeTicks); self }
115    /// The interval between BeginFrames that is reported to the compositor, in milliseconds.
116    /// Defaults to a 60 frames/second interval, i.e. about 16.666 milliseconds.
117    pub fn interval(mut self, interval: f64) -> Self { self.interval = Some(interval); self }
118    /// Whether updates should not be committed and drawn onto the display. False by default. If
119    /// true, only side effects of the BeginFrame will be run, such as layout and animations, but
120    /// any visual updates may not be visible on the display or in screenshots.
121    pub fn noDisplayUpdates(mut self, noDisplayUpdates: bool) -> Self { self.noDisplayUpdates = Some(noDisplayUpdates); self }
122    /// If set, a screenshot of the frame will be captured and returned in the response. Otherwise,
123    /// no screenshot will be captured. Note that capturing a screenshot can fail, for example,
124    /// during renderer initialization. In such a case, no screenshot data will be returned.
125    pub fn screenshot(mut self, screenshot: ScreenshotParams<'a>) -> Self { self.screenshot = Some(screenshot); self }
126    pub fn build(self) -> BeginFrameParams<'a> {
127        BeginFrameParams {
128            frameTimeTicks: self.frameTimeTicks,
129            interval: self.interval,
130            noDisplayUpdates: self.noDisplayUpdates,
131            screenshot: self.screenshot,
132        }
133    }
134}
135
136/// Sends a BeginFrame to the target and returns when the frame was completed. Optionally captures a
137/// screenshot from the resulting frame. Requires that the target was created with enabled
138/// BeginFrameControl. Designed for use with --run-all-compositor-stages-before-draw, see also
139/// https://goo.gle/chrome-headless-rendering for more background.
140
141#[derive(Debug, Clone, Serialize, Deserialize, Default)]
142#[serde(rename_all = "camelCase")]
143pub struct BeginFrameReturns<'a> {
144    /// Whether the BeginFrame resulted in damage and, thus, a new frame was committed to the
145    /// display. Reported for diagnostic uses, may be removed in the future.
146    hasDamage: bool,
147    /// Base64-encoded image data of the screenshot, if one was requested and successfully taken. (Encoded as a base64 string when passed over JSON)
148    #[serde(skip_serializing_if = "Option::is_none")]
149    screenshotData: Option<Cow<'a, str>>,
150}
151
152impl<'a> BeginFrameReturns<'a> {
153    pub fn builder(hasDamage: bool) -> BeginFrameReturnsBuilder<'a> {
154        BeginFrameReturnsBuilder {
155            hasDamage: hasDamage,
156            screenshotData: None,
157        }
158    }
159    pub fn hasDamage(&self) -> bool { self.hasDamage }
160    pub fn screenshotData(&self) -> Option<&str> { self.screenshotData.as_deref() }
161}
162
163
164pub struct BeginFrameReturnsBuilder<'a> {
165    hasDamage: bool,
166    screenshotData: Option<Cow<'a, str>>,
167}
168
169impl<'a> BeginFrameReturnsBuilder<'a> {
170    /// Base64-encoded image data of the screenshot, if one was requested and successfully taken. (Encoded as a base64 string when passed over JSON)
171    pub fn screenshotData(mut self, screenshotData: impl Into<Cow<'a, str>>) -> Self { self.screenshotData = Some(screenshotData.into()); self }
172    pub fn build(self) -> BeginFrameReturns<'a> {
173        BeginFrameReturns {
174            hasDamage: self.hasDamage,
175            screenshotData: self.screenshotData,
176        }
177    }
178}
179
180impl<'a> BeginFrameParams<'a> { pub const METHOD: &'static str = "HeadlessExperimental.beginFrame"; }
181
182impl<'a> crate::CdpCommand<'a> for BeginFrameParams<'a> {
183    const METHOD: &'static str = "HeadlessExperimental.beginFrame";
184    type Response = BeginFrameReturns<'a>;
185}
186
187#[derive(Debug, Clone, Serialize, Deserialize, Default)]
188pub struct DisableParams {}
189
190impl DisableParams { pub const METHOD: &'static str = "HeadlessExperimental.disable"; }
191
192impl<'a> crate::CdpCommand<'a> for DisableParams {
193    const METHOD: &'static str = "HeadlessExperimental.disable";
194    type Response = crate::EmptyReturns;
195}
196
197#[derive(Debug, Clone, Serialize, Deserialize, Default)]
198pub struct EnableParams {}
199
200impl EnableParams { pub const METHOD: &'static str = "HeadlessExperimental.enable"; }
201
202impl<'a> crate::CdpCommand<'a> for EnableParams {
203    const METHOD: &'static str = "HeadlessExperimental.enable";
204    type Response = crate::EmptyReturns;
205}