From 1ae117f67b63c0ce574b595a26cbad9fe309639d Mon Sep 17 00:00:00 2001 From: Josh Matthews Date: Tue, 14 Jul 2020 12:06:46 -0400 Subject: [PATCH 1/2] dom: Add stub implementation for HTMLCanvasElement.captureStream. --- components/config/prefs.rs | 3 +++ components/script/dom/htmlcanvaselement.rs | 15 +++++++++++++++ .../script/dom/webidls/HTMLCanvasElement.webidl | 5 +++++ resources/prefs.json | 1 + 4 files changed, 24 insertions(+) diff --git a/components/config/prefs.rs b/components/config/prefs.rs index bf78d8d584d..a3302e1f597 100644 --- a/components/config/prefs.rs +++ b/components/config/prefs.rs @@ -133,6 +133,9 @@ mod gen { enabled: bool, } }, + canvas_capture: { + enabled: bool, + }, canvas_text: { enabled: bool, }, diff --git a/components/script/dom/htmlcanvaselement.rs b/components/script/dom/htmlcanvaselement.rs index 4b7d54b323d..c9060c7d8f3 100644 --- a/components/script/dom/htmlcanvaselement.rs +++ b/components/script/dom/htmlcanvaselement.rs @@ -7,10 +7,12 @@ use crate::dom::bindings::cell::{ref_filter_map, DomRefCell, Ref}; use crate::dom::bindings::codegen::Bindings::HTMLCanvasElementBinding::{ HTMLCanvasElementMethods, RenderingContext, }; +use crate::dom::bindings::codegen::Bindings::MediaStreamBinding::MediaStreamMethods; use crate::dom::bindings::codegen::Bindings::WebGLRenderingContextBinding::WebGLContextAttributes; use crate::dom::bindings::conversions::ConversionResult; use crate::dom::bindings::error::{Error, Fallible}; use crate::dom::bindings::inheritance::Castable; +use crate::dom::bindings::num::Finite; use crate::dom::bindings::reflector::DomObject; use crate::dom::bindings::root::{Dom, DomRoot, LayoutDom}; use crate::dom::bindings::str::{DOMString, USVString}; @@ -22,6 +24,8 @@ use crate::dom::element::{AttributeMutation, Element, LayoutElementHelpers}; use crate::dom::globalscope::GlobalScope; use crate::dom::gpucanvascontext::GPUCanvasContext; use crate::dom::htmlelement::HTMLElement; +use crate::dom::mediastream::MediaStream; +use crate::dom::mediastreamtrack::MediaStreamTrack; use crate::dom::node::{window_from_node, Node}; use crate::dom::virtualmethods::VirtualMethods; use crate::dom::webgl2renderingcontext::WebGL2RenderingContext; @@ -41,6 +45,8 @@ use js::rust::HandleValue; use profile_traits::ipc; use script_layout_interface::{HTMLCanvasData, HTMLCanvasDataSource}; use script_traits::ScriptMsg; +use servo_media::streams::registry::MediaStreamId; +use servo_media::streams::MediaStreamType; use style::attr::{AttrValue, LengthOrPercentageOrAuto}; const DEFAULT_WIDTH: u32 = 300; @@ -429,6 +435,15 @@ impl HTMLCanvasElementMethods for HTMLCanvasElement { base64::encode_config_buf(&png, base64::STANDARD, &mut url); Ok(USVString(url)) } + + /// https://w3c.github.io/mediacapture-fromelement/#dom-htmlcanvaselement-capturestream + fn CaptureStream(&self, _frame_request_rate: Option>) -> DomRoot { + let global = self.global(); + let stream = MediaStream::new(&*global); + let track = MediaStreamTrack::new(&*global, MediaStreamId::new(), MediaStreamType::Video); + stream.AddTrack(&track); + stream + } } impl VirtualMethods for HTMLCanvasElement { diff --git a/components/script/dom/webidls/HTMLCanvasElement.webidl b/components/script/dom/webidls/HTMLCanvasElement.webidl index 650357a905e..5c33aa3532e 100644 --- a/components/script/dom/webidls/HTMLCanvasElement.webidl +++ b/components/script/dom/webidls/HTMLCanvasElement.webidl @@ -23,4 +23,9 @@ interface HTMLCanvasElement : HTMLElement { //OffscreenCanvas transferControlToOffscreen(); }; +partial interface HTMLCanvasElement { + [Pref="dom.canvas_capture.enabled"] + MediaStream captureStream (optional double frameRequestRate); +}; + //callback BlobCallback = void (Blob? blob); diff --git a/resources/prefs.json b/resources/prefs.json index 0b219f7966a..04ecb8f89b7 100644 --- a/resources/prefs.json +++ b/resources/prefs.json @@ -1,6 +1,7 @@ { "dom.bluetooth.enabled": false, "dom.bluetooth.testing.enabled": false, + "dom.canvas_capture.enabled": false, "dom.canvas_text.enabled": true, "dom.compositionevent.enabled": false, "dom.customelements.enabled": true, From 84efd56e57067568744aa3f492bae005db6a7c62 Mon Sep 17 00:00:00 2001 From: Josh Matthews Date: Tue, 14 Jul 2020 12:10:13 -0400 Subject: [PATCH 2/2] dom: Add WebRTC transceiver stubs. --- components/config/prefs.rs | 3 + components/script/dom/mod.rs | 2 + components/script/dom/rtcpeerconnection.rs | 14 ++++- components/script/dom/rtcrtpsender.rs | 57 +++++++++++++++++++ components/script/dom/rtcrtptransceiver.rs | 55 ++++++++++++++++++ .../dom/webidls/RTCPeerConnection.webidl | 21 ++++++- .../script/dom/webidls/RTCRtpSender.webidl | 47 +++++++++++++++ .../dom/webidls/RTCRtpTransceiver.webidl | 24 ++++++++ resources/prefs.json | 1 + 9 files changed, 220 insertions(+), 4 deletions(-) create mode 100644 components/script/dom/rtcrtpsender.rs create mode 100644 components/script/dom/rtcrtptransceiver.rs create mode 100644 components/script/dom/webidls/RTCRtpSender.webidl create mode 100644 components/script/dom/webidls/RTCRtpTransceiver.webidl diff --git a/components/config/prefs.rs b/components/config/prefs.rs index a3302e1f597..223a00f8826 100644 --- a/components/config/prefs.rs +++ b/components/config/prefs.rs @@ -256,6 +256,9 @@ mod gen { enabled: bool, }, webrtc: { + transceiver: { + enabled: bool, + }, #[serde(default)] enabled: bool, }, diff --git a/components/script/dom/mod.rs b/components/script/dom/mod.rs index 7508838c15d..82dc33bd7e3 100644 --- a/components/script/dom/mod.rs +++ b/components/script/dom/mod.rs @@ -498,6 +498,8 @@ pub mod rtcerrorevent; pub mod rtcicecandidate; pub mod rtcpeerconnection; pub mod rtcpeerconnectioniceevent; +pub(crate) mod rtcrtpsender; +pub(crate) mod rtcrtptransceiver; pub mod rtcsessiondescription; pub mod rtctrackevent; pub mod screen; diff --git a/components/script/dom/rtcpeerconnection.rs b/components/script/dom/rtcpeerconnection.rs index bd4ac712c96..9fd651e5a16 100644 --- a/components/script/dom/rtcpeerconnection.rs +++ b/components/script/dom/rtcpeerconnection.rs @@ -8,12 +8,12 @@ use crate::dom::bindings::codegen::Bindings::RTCIceCandidateBinding::RTCIceCandi use crate::dom::bindings::codegen::Bindings::RTCPeerConnectionBinding::RTCPeerConnectionMethods; use crate::dom::bindings::codegen::Bindings::RTCPeerConnectionBinding::{ RTCAnswerOptions, RTCBundlePolicy, RTCConfiguration, RTCIceConnectionState, - RTCIceGatheringState, RTCOfferOptions, RTCSignalingState, + RTCIceGatheringState, RTCOfferOptions, RTCRtpTransceiverInit, RTCSignalingState, }; use crate::dom::bindings::codegen::Bindings::RTCSessionDescriptionBinding::{ RTCSdpType, RTCSessionDescriptionInit, }; -use crate::dom::bindings::codegen::UnionTypes::StringOrStringSequence; +use crate::dom::bindings::codegen::UnionTypes::{MediaStreamTrackOrString, StringOrStringSequence}; use crate::dom::bindings::error::Error; use crate::dom::bindings::error::Fallible; use crate::dom::bindings::inheritance::Castable; @@ -32,6 +32,7 @@ use crate::dom::rtcdatachannel::RTCDataChannel; use crate::dom::rtcdatachannelevent::RTCDataChannelEvent; use crate::dom::rtcicecandidate::RTCIceCandidate; use crate::dom::rtcpeerconnectioniceevent::RTCPeerConnectionIceEvent; +use crate::dom::rtcrtptransceiver::RTCRtpTransceiver; use crate::dom::rtcsessiondescription::RTCSessionDescription; use crate::dom::rtctrackevent::RTCTrackEvent; use crate::dom::window::Window; @@ -744,6 +745,15 @@ impl RTCPeerConnectionMethods for RTCPeerConnection { ) -> DomRoot { RTCDataChannel::new(&self.global(), &self, label, init, None) } + + /// https://w3c.github.io/webrtc-pc/#dom-rtcpeerconnection-addtransceiver + fn AddTransceiver( + &self, + _track_or_kind: MediaStreamTrackOrString, + init: &RTCRtpTransceiverInit, + ) -> DomRoot { + RTCRtpTransceiver::new(&self.global(), init.direction) + } } impl From for RTCSessionDescriptionInit { diff --git a/components/script/dom/rtcrtpsender.rs b/components/script/dom/rtcrtpsender.rs new file mode 100644 index 00000000000..10be5a6d79a --- /dev/null +++ b/components/script/dom/rtcrtpsender.rs @@ -0,0 +1,57 @@ +/* This Source Code Form is subject to the terms of the Mozilla Public + * License, v. 2.0. If a copy of the MPL was not distributed with this + * file, You can obtain one at https://mozilla.org/MPL/2.0/. */ + +use crate::dom::bindings::codegen::Bindings::RTCRtpSenderBinding::RTCRtpSenderMethods; +use crate::dom::bindings::codegen::Bindings::RTCRtpSenderBinding::{ + RTCRtcpParameters, RTCRtpParameters, RTCRtpSendParameters, +}; +use crate::dom::bindings::reflector::{reflect_dom_object, DomObject, Reflector}; +use crate::dom::bindings::root::DomRoot; +use crate::dom::bindings::str::DOMString; +use crate::dom::globalscope::GlobalScope; +use crate::dom::promise::Promise; +use dom_struct::dom_struct; +use std::rc::Rc; + +#[dom_struct] +pub struct RTCRtpSender { + reflector_: Reflector, +} + +impl RTCRtpSender { + fn new_inherited() -> Self { + Self { + reflector_: Reflector::new(), + } + } + + pub(crate) fn new(global: &GlobalScope) -> DomRoot { + reflect_dom_object(Box::new(Self::new_inherited()), global) + } +} + +impl RTCRtpSenderMethods for RTCRtpSender { + // https://w3c.github.io/webrtc-pc/#dom-rtcrtpsender-getparameters + fn GetParameters(&self) -> RTCRtpSendParameters { + RTCRtpSendParameters { + parent: RTCRtpParameters { + headerExtensions: vec![], + rtcp: RTCRtcpParameters { + cname: None, + reducedSize: None, + }, + codecs: vec![], + }, + transactionId: DOMString::new(), + encodings: vec![], + } + } + + // https://w3c.github.io/webrtc-pc/#dom-rtcrtpsender-setparameters + fn SetParameters(&self, _parameters: &RTCRtpSendParameters) -> Rc { + let promise = Promise::new(&self.global()); + promise.resolve_native(&()); + promise + } +} diff --git a/components/script/dom/rtcrtptransceiver.rs b/components/script/dom/rtcrtptransceiver.rs new file mode 100644 index 00000000000..5c041bb1ae6 --- /dev/null +++ b/components/script/dom/rtcrtptransceiver.rs @@ -0,0 +1,55 @@ +/* This Source Code Form is subject to the terms of the Mozilla Public + * License, v. 2.0. If a copy of the MPL was not distributed with this + * file, You can obtain one at https://mozilla.org/MPL/2.0/. */ + +use crate::dom::bindings::codegen::Bindings::RTCRtpTransceiverBinding::{ + RTCRtpTransceiverDirection, RTCRtpTransceiverMethods, +}; +use crate::dom::bindings::reflector::{reflect_dom_object, Reflector}; +use crate::dom::bindings::root::{Dom, DomRoot}; +use crate::dom::globalscope::GlobalScope; +use crate::dom::rtcrtpsender::RTCRtpSender; +use dom_struct::dom_struct; +use std::cell::Cell; + +#[dom_struct] +pub struct RTCRtpTransceiver { + reflector_: Reflector, + sender: Dom, + direction: Cell, +} + +impl RTCRtpTransceiver { + fn new_inherited(global: &GlobalScope, direction: RTCRtpTransceiverDirection) -> Self { + let sender = RTCRtpSender::new(global); + Self { + reflector_: Reflector::new(), + direction: Cell::new(direction), + sender: Dom::from_ref(&*sender), + } + } + + pub(crate) fn new( + global: &GlobalScope, + direction: RTCRtpTransceiverDirection, + ) -> DomRoot { + reflect_dom_object(Box::new(Self::new_inherited(global, direction)), global) + } +} + +impl RTCRtpTransceiverMethods for RTCRtpTransceiver { + /// https://w3c.github.io/webrtc-pc/#dom-rtcrtptransceiver-direction + fn Direction(&self) -> RTCRtpTransceiverDirection { + self.direction.get() + } + + /// https://w3c.github.io/webrtc-pc/#dom-rtcrtptransceiver-direction + fn SetDirection(&self, direction: RTCRtpTransceiverDirection) { + self.direction.set(direction); + } + + /// https://w3c.github.io/webrtc-pc/#dom-rtcrtptransceiver-sender + fn Sender(&self) -> DomRoot { + DomRoot::from_ref(&*self.sender) + } +} diff --git a/components/script/dom/webidls/RTCPeerConnection.webidl b/components/script/dom/webidls/RTCPeerConnection.webidl index f53691a9a70..d75f2f9c14c 100644 --- a/components/script/dom/webidls/RTCPeerConnection.webidl +++ b/components/script/dom/webidls/RTCPeerConnection.webidl @@ -115,6 +115,22 @@ enum RTCSignalingState { "closed" }; +dictionary RTCRtpCodingParameters { + DOMString rid; +}; + +dictionary RTCRtpEncodingParameters : RTCRtpCodingParameters { + boolean active = true; + unsigned long maxBitrate; + double scaleResolutionDownBy; +}; + +dictionary RTCRtpTransceiverInit { + RTCRtpTransceiverDirection direction = "sendrecv"; + sequence streams = []; + sequence sendEncodings = []; +}; + partial interface RTCPeerConnection { // sequence getSenders(); // sequence getReceivers(); @@ -122,8 +138,9 @@ partial interface RTCPeerConnection { // RTCRtpSender addTrack(MediaStreamTrack track, // MediaStream... streams); // void removeTrack(RTCRtpSender sender); - // RTCRtpTransceiver addTransceiver((MediaStreamTrack or DOMString) trackOrKind, - // optional RTCRtpTransceiverInit init); + [Pref="dom.webrtc.transceiver.enabled"] + RTCRtpTransceiver addTransceiver((MediaStreamTrack or DOMString) trackOrKind, + optional RTCRtpTransceiverInit init = {}); attribute EventHandler ontrack; }; diff --git a/components/script/dom/webidls/RTCRtpSender.webidl b/components/script/dom/webidls/RTCRtpSender.webidl new file mode 100644 index 00000000000..d804b1bb3b7 --- /dev/null +++ b/components/script/dom/webidls/RTCRtpSender.webidl @@ -0,0 +1,47 @@ +/* This Source Code Form is subject to the terms of the Mozilla Public + * License, v. 2.0. If a copy of the MPL was not distributed with this + * file, You can obtain one at https://mozilla.org/MPL/2.0/. */ + +// https://w3c.github.io/webrtc-pc/#dom-rtcrtpsender + +dictionary RTCRtpHeaderExtensionParameters { + required DOMString uri; + required unsigned short id; + boolean encrypted = false; +}; + +dictionary RTCRtcpParameters { + DOMString cname; + boolean reducedSize; +}; + +dictionary RTCRtpCodecParameters { + required octet payloadType; + required DOMString mimeType; + required unsigned long clockRate; + unsigned short channels; + DOMString sdpFmtpLine; +}; + +dictionary RTCRtpParameters { + required sequence headerExtensions; + required RTCRtcpParameters rtcp; + required sequence codecs; +}; + +dictionary RTCRtpSendParameters : RTCRtpParameters { + required DOMString transactionId; + required sequence encodings; +}; + +[Exposed=Window, Pref="dom.webrtc.transceiver.enabled"] +interface RTCRtpSender { + //readonly attribute MediaStreamTrack? track; + //readonly attribute RTCDtlsTransport? transport; + //static RTCRtpCapabilities? getCapabilities(DOMString kind); + Promise setParameters(RTCRtpSendParameters parameters); + RTCRtpSendParameters getParameters(); + //Promise replaceTrack(MediaStreamTrack? withTrack); + //void setStreams(MediaStream... streams); + //Promise getStats(); +}; diff --git a/components/script/dom/webidls/RTCRtpTransceiver.webidl b/components/script/dom/webidls/RTCRtpTransceiver.webidl new file mode 100644 index 00000000000..408c2708709 --- /dev/null +++ b/components/script/dom/webidls/RTCRtpTransceiver.webidl @@ -0,0 +1,24 @@ +/* This Source Code Form is subject to the terms of the Mozilla Public + * License, v. 2.0. If a copy of the MPL was not distributed with this + * file, You can obtain one at https://mozilla.org/MPL/2.0/. */ + +// https://w3c.github.io/webrtc-pc/#rtcrtptransceiver-interface + +[Exposed=Window, Pref="dom.webrtc.transceiver.enabled"] +interface RTCRtpTransceiver { + //readonly attribute DOMString? mid; + [SameObject] readonly attribute RTCRtpSender sender; + //[SameObject] readonly attribute RTCRtpReceiver receiver; + attribute RTCRtpTransceiverDirection direction; + //readonly attribute RTCRtpTransceiverDirection? currentDirection; + //void stop(); + //void setCodecPreferences(sequence codecs); +}; + +enum RTCRtpTransceiverDirection { + "sendrecv", + "sendonly", + "recvonly", + "inactive", + "stopped" +}; diff --git a/resources/prefs.json b/resources/prefs.json index 04ecb8f89b7..7cb4bdaedb3 100644 --- a/resources/prefs.json +++ b/resources/prefs.json @@ -30,6 +30,7 @@ "dom.webgl2.enabled": false, "dom.webgpu.enabled": false, "dom.webrtc.enabled": false, + "dom.webrtc.transceiver.enabled": false, "dom.webvr.enabled": false, "dom.webvr.event_polling_interval": 500, "dom.webvr.test": false,