aboutsummaryrefslogtreecommitdiffstats
path: root/components/script
diff options
context:
space:
mode:
Diffstat (limited to 'components/script')
-rw-r--r--components/script/Cargo.toml2
-rw-r--r--components/script/dom/bindings/global.rs11
-rw-r--r--components/script/dom/bindings/trace.rs3
-rw-r--r--components/script/dom/element.rs6
-rw-r--r--components/script/dom/htmlbodyelement.rs10
-rw-r--r--components/script/dom/htmlelement.rs10
-rw-r--r--components/script/dom/htmlformelement.rs2
-rw-r--r--components/script/dom/htmlhrelement.rs7
-rw-r--r--components/script/dom/htmlinputelement.rs170
-rw-r--r--components/script/dom/mimetype.rs36
-rw-r--r--components/script/dom/mimetypearray.rs62
-rw-r--r--components/script/dom/mod.rs4
-rw-r--r--components/script/dom/navigator.rs21
-rw-r--r--components/script/dom/node.rs8
-rw-r--r--components/script/dom/plugin.rs61
-rw-r--r--components/script/dom/pluginarray.rs67
-rw-r--r--components/script/dom/webglprogram.rs11
-rw-r--r--components/script/dom/webglrenderingcontext.rs56
-rw-r--r--components/script/dom/webglshader.rs1
-rw-r--r--components/script/dom/webidls/CSSStyleDeclaration.webidl1
-rw-r--r--components/script/dom/webidls/HTMLHRElement.webidl2
-rw-r--r--components/script/dom/webidls/HTMLInputElement.webidl20
-rw-r--r--components/script/dom/webidls/MimeType.webidl12
-rw-r--r--components/script/dom/webidls/MimeTypeArray.webidl12
-rw-r--r--components/script/dom/webidls/Navigator.webidl10
-rw-r--r--components/script/dom/webidls/Plugin.webidl15
-rw-r--r--components/script/dom/webidls/PluginArray.webidl13
-rw-r--r--components/script/dom/webidls/WebGLRenderingContext.webidl2
-rw-r--r--components/script/dom/xmlhttprequest.rs2
-rw-r--r--components/script/script_runtime.rs177
-rw-r--r--components/script/script_thread.rs3
31 files changed, 714 insertions, 103 deletions
diff --git a/components/script/Cargo.toml b/components/script/Cargo.toml
index 6a8a5d1b25e..eaf86e3b39f 100644
--- a/components/script/Cargo.toml
+++ b/components/script/Cargo.toml
@@ -91,7 +91,7 @@ rustc-serialize = "0.3"
selectors = {version = "0.5", features = ["heap_size"]}
serde = "0.7"
smallvec = "0.1"
-string_cache = {version = "0.2.11", features = ["heap_size", "unstable"]}
+string_cache = {version = "0.2.12", features = ["heap_size", "unstable"]}
time = "0.1.12"
unicase = "1.0"
url = {version = "0.5.7", features = ["heap_size"]}
diff --git a/components/script/dom/bindings/global.rs b/components/script/dom/bindings/global.rs
index 9cac7d9b940..e50f8ace9d0 100644
--- a/components/script/dom/bindings/global.rs
+++ b/components/script/dom/bindings/global.rs
@@ -143,6 +143,17 @@ impl<'a> GlobalRef<'a> {
}
}
+ /// Get the [base url](https://html.spec.whatwg.org/multipage/#api-base-url)
+ /// for this global scope.
+ pub fn api_base_url(&self) -> Url {
+ match *self {
+ // https://html.spec.whatwg.org/multipage/#script-settings-for-browsing-contexts:api-base-url
+ GlobalRef::Window(ref window) => window.Document().base_url(),
+ // https://html.spec.whatwg.org/multipage/#script-settings-for-workers:api-base-url
+ GlobalRef::Worker(ref worker) => worker.get_url().clone(),
+ }
+ }
+
/// `ScriptChan` used to send messages to the event loop of this global's
/// thread.
pub fn script_chan(&self) -> Box<ScriptChan + Send> {
diff --git a/components/script/dom/bindings/trace.rs b/components/script/dom/bindings/trace.rs
index 9cc2d13fb77..16138b33641 100644
--- a/components/script/dom/bindings/trace.rs
+++ b/components/script/dom/bindings/trace.rs
@@ -62,6 +62,7 @@ use net_traits::image::base::{Image, ImageMetadata};
use net_traits::image_cache_thread::{ImageCacheChan, ImageCacheThread};
use net_traits::response::HttpsState;
use net_traits::storage_thread::StorageType;
+use offscreen_gl_context::GLLimits;
use profile_traits::mem::ProfilerChan as MemProfilerChan;
use profile_traits::time::ProfilerChan as TimeProfilerChan;
use script_runtime::ScriptChan;
@@ -308,7 +309,7 @@ no_jsmanaged_fields!(StorageType);
no_jsmanaged_fields!(CanvasGradientStop, LinearGradientStyle, RadialGradientStyle);
no_jsmanaged_fields!(LineCapStyle, LineJoinStyle, CompositionOrBlending);
no_jsmanaged_fields!(RepetitionStyle);
-no_jsmanaged_fields!(WebGLError);
+no_jsmanaged_fields!(WebGLError, GLLimits);
no_jsmanaged_fields!(TimeProfilerChan);
no_jsmanaged_fields!(MemProfilerChan);
no_jsmanaged_fields!(PseudoElement);
diff --git a/components/script/dom/element.rs b/components/script/dom/element.rs
index 4e2af78f31a..f27bc3a35fb 100644
--- a/components/script/dom/element.rs
+++ b/components/script/dom/element.rs
@@ -377,7 +377,7 @@ impl LayoutElementHelpers for LayoutJS<Element> {
},
// Others
_ => {
- match this.get_size_for_layout() {
+ match this.size_for_layout() {
0 => None,
s => Some(s as i32),
}
@@ -571,7 +571,7 @@ impl LayoutElementHelpers for LayoutJS<Element> {
// TODO option and menuitem can also have a checked state.
match self.downcast::<HTMLInputElement>() {
Some(input) => unsafe {
- input.get_checked_state_for_layout()
+ input.checked_state_for_layout()
},
None => false,
}
@@ -583,7 +583,7 @@ impl LayoutElementHelpers for LayoutJS<Element> {
// TODO progress elements can also be matched with :indeterminate
match self.downcast::<HTMLInputElement>() {
Some(input) => unsafe {
- input.get_indeterminate_state_for_layout()
+ input.indeterminate_state_for_layout()
},
None => false,
}
diff --git a/components/script/dom/htmlbodyelement.rs b/components/script/dom/htmlbodyelement.rs
index 8ac184ea51d..ca133b88dbb 100644
--- a/components/script/dom/htmlbodyelement.rs
+++ b/components/script/dom/htmlbodyelement.rs
@@ -47,6 +47,16 @@ impl HTMLBodyElement {
let element = HTMLBodyElement::new_inherited(localName, prefix, document);
Node::reflect_node(box element, document, HTMLBodyElementBinding::Wrap)
}
+
+ /// https://drafts.csswg.org/cssom-view/#the-html-body-element
+ pub fn is_the_html_body_element(&self) -> bool {
+ let self_node = self.upcast::<Node>();
+ let root_elem = self.upcast::<Element>().root_element();
+ let root_node = root_elem.upcast::<Node>();
+ root_node.is_parent_of(self_node) &&
+ self_node.preceding_siblings().all(|n| !n.is::<HTMLBodyElement>())
+ }
+
}
impl HTMLBodyElementMethods for HTMLBodyElement {
diff --git a/components/script/dom/htmlelement.rs b/components/script/dom/htmlelement.rs
index b3c95f89127..566a86d8804 100644
--- a/components/script/dom/htmlelement.rs
+++ b/components/script/dom/htmlelement.rs
@@ -233,7 +233,7 @@ impl HTMLElementMethods for HTMLElement {
document.commit_focus_transaction(FocusType::Element);
}
- // https://drafts.csswg.org/cssom-view/#extensions-to-the-htmlelement-interface
+ // https://drafts.csswg.org/cssom-view/#dom-htmlelement-offsetparent
fn GetOffsetParent(&self) -> Option<Root<Element>> {
if self.is::<HTMLBodyElement>() || self.is::<HTMLHtmlElement>() {
return None;
@@ -246,7 +246,7 @@ impl HTMLElementMethods for HTMLElement {
element
}
- // https://drafts.csswg.org/cssom-view/#extensions-to-the-htmlelement-interface
+ // https://drafts.csswg.org/cssom-view/#dom-htmlelement-offsettop
fn OffsetTop(&self) -> i32 {
if self.is::<HTMLBodyElement>() {
return 0;
@@ -259,7 +259,7 @@ impl HTMLElementMethods for HTMLElement {
rect.origin.y.to_nearest_px()
}
- // https://drafts.csswg.org/cssom-view/#extensions-to-the-htmlelement-interface
+ // https://drafts.csswg.org/cssom-view/#dom-htmlelement-offsetleft
fn OffsetLeft(&self) -> i32 {
if self.is::<HTMLBodyElement>() {
return 0;
@@ -272,7 +272,7 @@ impl HTMLElementMethods for HTMLElement {
rect.origin.x.to_nearest_px()
}
- // https://drafts.csswg.org/cssom-view/#extensions-to-the-htmlelement-interface
+ // https://drafts.csswg.org/cssom-view/#dom-htmlelement-offsetwidth
fn OffsetWidth(&self) -> i32 {
let node = self.upcast::<Node>();
let window = window_from_node(self);
@@ -281,7 +281,7 @@ impl HTMLElementMethods for HTMLElement {
rect.size.width.to_nearest_px()
}
- // https://drafts.csswg.org/cssom-view/#extensions-to-the-htmlelement-interface
+ // https://drafts.csswg.org/cssom-view/#dom-htmlelement-offsetheight
fn OffsetHeight(&self) -> i32 {
let node = self.upcast::<Node>();
let window = window_from_node(self);
diff --git a/components/script/dom/htmlformelement.rs b/components/script/dom/htmlformelement.rs
index 70a2a7ad730..3e7421de443 100644
--- a/components/script/dom/htmlformelement.rs
+++ b/components/script/dom/htmlformelement.rs
@@ -414,7 +414,7 @@ impl HTMLFormElement {
HTMLElementTypeId::HTMLInputElement => {
let input = child.downcast::<HTMLInputElement>().unwrap();
// Step 3.2-3.7
- if let Some(datum) = input.get_form_datum(submitter) {
+ if let Some(datum) = input.form_datum(submitter) {
data_set.push(datum);
}
}
diff --git a/components/script/dom/htmlhrelement.rs b/components/script/dom/htmlhrelement.rs
index 93fdebbc954..bea12efbfea 100644
--- a/components/script/dom/htmlhrelement.rs
+++ b/components/script/dom/htmlhrelement.rs
@@ -37,6 +37,12 @@ impl HTMLHRElement {
}
impl HTMLHRElementMethods for HTMLHRElement {
+ // https://html.spec.whatwg.org/multipage/#dom-hr-align
+ make_getter!(Align, "align");
+
+ // https://html.spec.whatwg.org/multipage/#dom-hr-align
+ make_atomic_setter!(SetAlign, "align");
+
// https://html.spec.whatwg.org/multipage/#dom-hr-color
make_getter!(Color, "color");
@@ -86,6 +92,7 @@ impl VirtualMethods for HTMLHRElement {
fn parse_plain_attribute(&self, name: &Atom, value: DOMString) -> AttrValue {
match name {
+ &atom!("align") => AttrValue::from_dimension(value),
&atom!("color") => AttrValue::from_legacy_color(value),
&atom!("width") => AttrValue::from_dimension(value),
_ => self.super_type().unwrap().parse_plain_attribute(name, value),
diff --git a/components/script/dom/htmlinputelement.rs b/components/script/dom/htmlinputelement.rs
index 174a312448f..9c969ceec98 100644
--- a/components/script/dom/htmlinputelement.rs
+++ b/components/script/dom/htmlinputelement.rs
@@ -164,7 +164,7 @@ impl HTMLInputElement {
}
// https://html.spec.whatwg.org/multipage/#input-type-attr-summary
- fn get_value_mode(&self) -> ValueMode {
+ fn value_mode(&self) -> ValueMode {
match self.input_type.get() {
InputType::InputSubmit |
InputType::InputReset |
@@ -208,15 +208,15 @@ impl HTMLInputElement {
pub trait LayoutHTMLInputElementHelpers {
#[allow(unsafe_code)]
- unsafe fn get_value_for_layout(self) -> String;
+ unsafe fn value_for_layout(self) -> String;
#[allow(unsafe_code)]
- unsafe fn get_size_for_layout(self) -> u32;
+ unsafe fn size_for_layout(self) -> u32;
#[allow(unsafe_code)]
- unsafe fn get_selection_for_layout(self) -> Option<Range<isize>>;
+ unsafe fn selection_for_layout(self) -> Option<Range<isize>>;
#[allow(unsafe_code)]
- unsafe fn get_checked_state_for_layout(self) -> bool;
+ unsafe fn checked_state_for_layout(self) -> bool;
#[allow(unsafe_code)]
- unsafe fn get_indeterminate_state_for_layout(self) -> bool;
+ unsafe fn indeterminate_state_for_layout(self) -> bool;
}
#[allow(unsafe_code)]
@@ -226,7 +226,7 @@ unsafe fn get_raw_textinput_value(input: LayoutJS<HTMLInputElement>) -> DOMStrin
impl LayoutHTMLInputElementHelpers for LayoutJS<HTMLInputElement> {
#[allow(unsafe_code)]
- unsafe fn get_value_for_layout(self) -> String {
+ unsafe fn value_for_layout(self) -> String {
#[allow(unsafe_code)]
unsafe fn get_raw_attr_value(input: LayoutJS<HTMLInputElement>, default: &str) -> String {
let elem = input.upcast::<Element>();
@@ -245,7 +245,7 @@ impl LayoutHTMLInputElementHelpers for LayoutJS<HTMLInputElement> {
InputType::InputPassword => {
let text = get_raw_textinput_value(self);
if !text.is_empty() {
- // The implementation of get_selection_for_layout expects a 1:1 mapping of chars.
+ // The implementation of selection_for_layout expects a 1:1 mapping of chars.
text.chars().map(|_| '●').collect()
} else {
String::from((*self.unsafe_get()).placeholder.borrow_for_layout().clone())
@@ -254,7 +254,7 @@ impl LayoutHTMLInputElementHelpers for LayoutJS<HTMLInputElement> {
_ => {
let text = get_raw_textinput_value(self);
if !text.is_empty() {
- // The implementation of get_selection_for_layout expects a 1:1 mapping of chars.
+ // The implementation of selection_for_layout expects a 1:1 mapping of chars.
String::from(text)
} else {
String::from((*self.unsafe_get()).placeholder.borrow_for_layout().clone())
@@ -265,19 +265,19 @@ impl LayoutHTMLInputElementHelpers for LayoutJS<HTMLInputElement> {
#[allow(unrooted_must_root)]
#[allow(unsafe_code)]
- unsafe fn get_size_for_layout(self) -> u32 {
+ unsafe fn size_for_layout(self) -> u32 {
(*self.unsafe_get()).size.get()
}
#[allow(unrooted_must_root)]
#[allow(unsafe_code)]
- unsafe fn get_selection_for_layout(self) -> Option<Range<isize>> {
+ unsafe fn selection_for_layout(self) -> Option<Range<isize>> {
if !(*self.unsafe_get()).upcast::<Element>().focus_state() {
return None;
}
// Use the raw textinput to get the index as long as we use a 1:1 char mapping
- // in get_value_for_layout.
+ // in value_for_layout.
let raw = match (*self.unsafe_get()).input_type.get() {
InputType::InputText |
InputType::InputPassword => get_raw_textinput_value(self),
@@ -293,18 +293,37 @@ impl LayoutHTMLInputElementHelpers for LayoutJS<HTMLInputElement> {
#[allow(unrooted_must_root)]
#[allow(unsafe_code)]
- unsafe fn get_checked_state_for_layout(self) -> bool {
+ unsafe fn checked_state_for_layout(self) -> bool {
self.upcast::<Element>().get_state_for_layout().contains(IN_CHECKED_STATE)
}
#[allow(unrooted_must_root)]
#[allow(unsafe_code)]
- unsafe fn get_indeterminate_state_for_layout(self) -> bool {
+ unsafe fn indeterminate_state_for_layout(self) -> bool {
self.upcast::<Element>().get_state_for_layout().contains(IN_INDETERMINATE_STATE)
}
}
impl HTMLInputElementMethods for HTMLInputElement {
+
+ // https://html.spec.whatwg.org/multipage/#attr-input-accept
+ make_getter!(Accept, "accept");
+
+ // https://html.spec.whatwg.org/multipage/#attr-input-accept
+ make_setter!(SetAccept, "accept");
+
+ // https://html.spec.whatwg.org/multipage/#attr-input-alt
+ make_getter!(Alt, "alt");
+
+ // https://html.spec.whatwg.org/multipage/#attr-input-alt
+ make_setter!(SetAlt, "alt");
+
+ // https://html.spec.whatwg.org/multipage/#attr-input-dirName
+ make_getter!(DirName, "dirname");
+
+ // https://html.spec.whatwg.org/multipage/#attr-input-dirName
+ make_setter!(SetDirName, "dirname");
+
// https://html.spec.whatwg.org/multipage/#dom-fe-disabled
make_bool_getter!(Disabled, "disabled");
@@ -361,7 +380,7 @@ impl HTMLInputElementMethods for HTMLInputElement {
// https://html.spec.whatwg.org/multipage/#dom-input-value
fn Value(&self) -> DOMString {
- match self.get_value_mode() {
+ match self.value_mode() {
ValueMode::Value => self.textinput.borrow().get_content(),
ValueMode::Default => {
self.upcast::<Element>()
@@ -384,7 +403,7 @@ impl HTMLInputElementMethods for HTMLInputElement {
// https://html.spec.whatwg.org/multipage/#dom-input-value
fn SetValue(&self, value: DOMString) -> ErrorResult {
- match self.get_value_mode() {
+ match self.value_mode() {
ValueMode::Value => {
self.textinput.borrow_mut().set_content(value);
self.value_dirty.set(true);
@@ -458,12 +477,54 @@ impl HTMLInputElementMethods for HTMLInputElement {
// https://html.spec.whatwg.org/multipage/#attr-fs-formnovalidate
make_bool_setter!(SetFormNoValidate, "formnovalidate");
+ // https://html.spec.whatwg.org/multipage/#attr-input-max
+ make_getter!(Max, "max");
+
+ // https://html.spec.whatwg.org/multipage/#attr-input-max
+ make_setter!(SetMax, "max");
+
// https://html.spec.whatwg.org/multipage/#dom-input-maxlength
make_int_getter!(MaxLength, "maxlength", DEFAULT_MAX_LENGTH);
// https://html.spec.whatwg.org/multipage/#dom-input-maxlength
make_limited_int_setter!(SetMaxLength, "maxlength", DEFAULT_MAX_LENGTH);
+ // https://html.spec.whatwg.org/multipage/#attr-input-min
+ make_getter!(Min, "min");
+
+ // https://html.spec.whatwg.org/multipage/#attr-input-min
+ make_setter!(SetMin, "min");
+
+ // https://html.spec.whatwg.org/multipage/#attr-input-multiple
+ make_bool_getter!(Multiple, "multiple");
+
+ // https://html.spec.whatwg.org/multipage/#attr-input-multiple
+ make_bool_setter!(SetMultiple, "multiple");
+
+ // https://html.spec.whatwg.org/multipage/#attr-input-pattern
+ make_getter!(Pattern, "pattern");
+
+ // https://html.spec.whatwg.org/multipage/#attr-input-pattern
+ make_setter!(SetPattern, "pattern");
+
+ // https://html.spec.whatwg.org/multipage/#attr-input-required
+ make_bool_getter!(Required, "required");
+
+ // https://html.spec.whatwg.org/multipage/#attr-input-required
+ make_bool_setter!(SetRequired, "required");
+
+ // https://html.spec.whatwg.org/multipage/#attr-input-src
+ make_getter!(Src, "src");
+
+ // https://html.spec.whatwg.org/multipage/#attr-input-src
+ make_setter!(SetSrc, "src");
+
+ // https://html.spec.whatwg.org/multipage/#attr-input-step
+ make_getter!(Step, "step");
+
+ // https://html.spec.whatwg.org/multipage/#attr-input-step
+ make_setter!(SetStep, "step");
+
// https://html.spec.whatwg.org/multipage/#dom-input-indeterminate
fn Indeterminate(&self) -> bool {
self.upcast::<Element>().state().contains(IN_INDETERMINATE_STATE)
@@ -581,7 +642,7 @@ fn in_same_group(other: &HTMLInputElement, owner: Option<&HTMLFormElement>,
other.input_type.get() == InputType::InputRadio &&
// TODO Both a and b are in the same home subtree.
other.form_owner().r() == owner &&
- match (other.get_radio_group_name(), group) {
+ match (other.radio_group_name(), group) {
(Some(ref s1), Some(s2)) => compatibility_caseless_match_str(s1, s2) && s2 != &atom!(""),
_ => false
}
@@ -596,7 +657,7 @@ impl HTMLInputElement {
/// https://html.spec.whatwg.org/multipage/#constructing-the-form-data-set
/// Steps range from 3.1 to 3.7 which related to the HTMLInputElement
- pub fn get_form_datum(&self, submitter: Option<FormSubmitter>) -> Option<FormDatum> {
+ pub fn form_datum(&self, submitter: Option<FormSubmitter>) -> Option<FormDatum> {
// Step 3.2
let ty = self.type_();
// Step 3.4
@@ -632,7 +693,7 @@ impl HTMLInputElement {
}
// https://html.spec.whatwg.org/multipage/#radio-button-group
- fn get_radio_group_name(&self) -> Option<Atom> {
+ fn radio_group_name(&self) -> Option<Atom> {
//TODO: determine form owner
self.upcast::<Element>()
.get_attribute(&ns!(), &atom!("name"))
@@ -648,19 +709,15 @@ impl HTMLInputElement {
if self.input_type.get() == InputType::InputRadio && checked {
broadcast_radio_checked(self,
- self.get_radio_group_name().as_ref());
+ self.radio_group_name().as_ref());
}
self.upcast::<Node>().dirty(NodeDamage::OtherNodeDamage);
//TODO: dispatch change event
}
- pub fn get_indeterminate_state(&self) -> bool {
- self.Indeterminate()
- }
-
// https://html.spec.whatwg.org/multipage/#concept-fe-mutable
- fn mutable(&self) -> bool {
+ fn is_mutable(&self) -> bool {
// https://html.spec.whatwg.org/multipage/#the-input-element:concept-fe-mutable
// https://html.spec.whatwg.org/multipage/#the-readonly-attribute:concept-fe-mutable
!(self.upcast::<Element>().disabled_state() || self.ReadOnly())
@@ -740,9 +797,9 @@ impl VirtualMethods for HTMLInputElement {
};
// https://html.spec.whatwg.org/multipage/#input-type-change
- let (old_value_mode, old_idl_value) = (self.get_value_mode(), self.Value());
+ let (old_value_mode, old_idl_value) = (self.value_mode(), self.Value());
self.input_type.set(new_type);
- let new_value_mode = self.get_value_mode();
+ let new_value_mode = self.value_mode();
match (&old_value_mode, old_idl_value.is_empty(), new_value_mode) {
@@ -774,7 +831,7 @@ impl VirtualMethods for HTMLInputElement {
// Step 5
if new_type == InputType::InputRadio {
self.radio_group_updated(
- self.get_radio_group_name().as_ref());
+ self.radio_group_name().as_ref());
}
// TODO: Step 6 - value sanitization
@@ -783,7 +840,7 @@ impl VirtualMethods for HTMLInputElement {
if self.input_type.get() == InputType::InputRadio {
broadcast_radio_checked(
self,
- self.get_radio_group_name().as_ref());
+ self.radio_group_name().as_ref());
}
self.input_type.set(InputType::InputText);
}
@@ -916,7 +973,7 @@ impl Activatable for HTMLInputElement {
// https://html.spec.whatwg.org/multipage/#checkbox-state-%28type=checkbox%29:activation-behaviour-2
// https://html.spec.whatwg.org/multipage/#radio-button-state-%28type=radio%29:activation-behaviour-2
InputType::InputSubmit | InputType::InputReset
- | InputType::InputCheckbox | InputType::InputRadio => self.mutable(),
+ | InputType::InputCheckbox | InputType::InputRadio => self.is_mutable(),
_ => false
}
}
@@ -927,7 +984,7 @@ impl Activatable for HTMLInputElement {
let mut cache = self.activation_state.borrow_mut();
let ty = self.input_type.get();
cache.old_type = ty;
- cache.was_mutable = self.mutable();
+ cache.was_mutable = self.is_mutable();
if cache.was_mutable {
match ty {
// https://html.spec.whatwg.org/multipage/#submit-button-state-(type=submit):activation-behavior
@@ -952,7 +1009,7 @@ impl Activatable for HTMLInputElement {
let owner = self.form_owner();
let doc = document_from_node(self);
let doc_node = doc.upcast::<Node>();
- let group = self.get_radio_group_name();;
+ let group = self.radio_group_name();;
// Safe since we only manipulate the DOM tree after finding an element
let checked_member = doc_node.query_selector_iter(DOMString::from("input[type=radio]"))
@@ -998,16 +1055,12 @@ impl Activatable for HTMLInputElement {
InputType::InputRadio => {
// We want to restore state only if the element had been changed in the first place
if cache.was_mutable {
- let name = self.get_radio_group_name();
match cache.checked_radio.r() {
Some(o) => {
// Avoiding iterating through the whole tree here, instead
// we can check if the conditions for radio group siblings apply
- if name == o.get_radio_group_name() && // TODO should be compatibility caseless
- self.form_owner() == o.form_owner() &&
- // TODO Both a and b are in the same home subtree
- o.input_type.get() == InputType::InputRadio {
- o.SetChecked(true);
+ if in_same_group(&o, self.form_owner().r(), self.radio_group_name().as_ref()) {
+ o.SetChecked(true);
} else {
self.SetChecked(false);
}
@@ -1024,8 +1077,8 @@ impl Activatable for HTMLInputElement {
// https://html.spec.whatwg.org/multipage/#run-post-click-activation-steps
fn activation_behavior(&self, _event: &Event, _target: &EventTarget) {
let ty = self.input_type.get();
- if self.activation_state.borrow().old_type != ty {
- // Type changed, abandon ship
+ if self.activation_state.borrow().old_type != ty || !self.is_mutable() {
+ // Type changed or input is immutable, abandon ship
// https://www.w3.org/Bugs/Public/show_bug.cgi?id=27414
return;
}
@@ -1033,34 +1086,31 @@ impl Activatable for HTMLInputElement {
InputType::InputSubmit => {
// https://html.spec.whatwg.org/multipage/#submit-button-state-(type=submit):activation-behavior
// FIXME (Manishearth): support document owners (needs ability to get parent browsing context)
- if self.mutable() /* and document owner is fully active */ {
- self.form_owner().map(|o| {
- o.submit(SubmittedFrom::NotFromFormSubmitMethod,
- FormSubmitter::InputElement(self.clone()))
- });
- }
+ // Check if document owner is fully active
+ self.form_owner().map(|o| {
+ o.submit(SubmittedFrom::NotFromFormSubmitMethod,
+ FormSubmitter::InputElement(self.clone()))
+ });
},
InputType::InputReset => {
// https://html.spec.whatwg.org/multipage/#reset-button-state-(type=reset):activation-behavior
// FIXME (Manishearth): support document owners (needs ability to get parent browsing context)
- if self.mutable() /* and document owner is fully active */ {
- self.form_owner().map(|o| {
- o.reset(ResetFrom::NotFromFormResetMethod)
- });
- }
+ // Check if document owner is fully active
+ self.form_owner().map(|o| {
+ o.reset(ResetFrom::NotFromFormResetMethod)
+ });
},
InputType::InputCheckbox | InputType::InputRadio => {
// https://html.spec.whatwg.org/multipage/#checkbox-state-(type=checkbox):activation-behavior
// https://html.spec.whatwg.org/multipage/#radio-button-state-(type=radio):activation-behavior
- if self.mutable() {
- let target = self.upcast::<EventTarget>();
- target.fire_event("input",
- EventBubbles::Bubbles,
- EventCancelable::NotCancelable);
- target.fire_event("change",
- EventBubbles::Bubbles,
- EventCancelable::NotCancelable);
- }
+ // Check if document owner is fully active
+ let target = self.upcast::<EventTarget>();
+ target.fire_event("input",
+ EventBubbles::Bubbles,
+ EventCancelable::NotCancelable);
+ target.fire_event("change",
+ EventBubbles::Bubbles,
+ EventCancelable::NotCancelable);
},
_ => ()
}
diff --git a/components/script/dom/mimetype.rs b/components/script/dom/mimetype.rs
new file mode 100644
index 00000000000..f29b40faa5a
--- /dev/null
+++ b/components/script/dom/mimetype.rs
@@ -0,0 +1,36 @@
+/* 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 http://mozilla.org/MPL/2.0/. */
+
+use dom::bindings::codegen::Bindings::MimeTypeBinding::MimeTypeMethods;
+use dom::bindings::js::Root;
+use dom::bindings::reflector::{Reflector};
+use dom::plugin::Plugin;
+use util::str::DOMString;
+
+#[dom_struct]
+pub struct MimeType {
+ reflector_: Reflector,
+}
+
+impl MimeTypeMethods for MimeType {
+ // https://html.spec.whatwg.org/multipage/#dom-mimetype-type
+ fn Type(&self) -> DOMString {
+ unreachable!()
+ }
+
+ // https://html.spec.whatwg.org/multipage/#dom-mimetype-description
+ fn Description(&self) -> DOMString {
+ unreachable!()
+ }
+
+ // https://html.spec.whatwg.org/multipage/#dom-mimetype-suffixes
+ fn Suffixes(&self) -> DOMString {
+ unreachable!()
+ }
+
+ // https://html.spec.whatwg.org/multipage/#dom-mimetype-enabledplugin
+ fn EnabledPlugin(&self) -> Root<Plugin> {
+ unreachable!()
+ }
+}
diff --git a/components/script/dom/mimetypearray.rs b/components/script/dom/mimetypearray.rs
new file mode 100644
index 00000000000..ae11341e77b
--- /dev/null
+++ b/components/script/dom/mimetypearray.rs
@@ -0,0 +1,62 @@
+/* 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 http://mozilla.org/MPL/2.0/. */
+
+use dom::bindings::codegen::Bindings::MimeTypeArrayBinding;
+use dom::bindings::codegen::Bindings::MimeTypeArrayBinding::MimeTypeArrayMethods;
+use dom::bindings::global::GlobalRef;
+use dom::bindings::js::Root;
+use dom::bindings::reflector::{Reflector, reflect_dom_object};
+use dom::mimetype::MimeType;
+use util::str::DOMString;
+
+#[dom_struct]
+pub struct MimeTypeArray {
+ reflector_: Reflector,
+}
+
+impl MimeTypeArray {
+ pub fn new_inherited() -> MimeTypeArray {
+ MimeTypeArray {
+ reflector_: Reflector::new()
+ }
+ }
+
+ pub fn new(global: GlobalRef) -> Root<MimeTypeArray> {
+ reflect_dom_object(box MimeTypeArray::new_inherited(),
+ global,
+ MimeTypeArrayBinding::Wrap)
+ }
+}
+
+impl MimeTypeArrayMethods for MimeTypeArray {
+ // https://html.spec.whatwg.org/multipage/#dom-mimetypearray-length
+ fn Length(&self) -> u32 {
+ 0
+ }
+
+ // https://html.spec.whatwg.org/multipage/#dom-mimetypearray-item
+ fn Item(&self, _index: u32) -> Option<Root<MimeType>> {
+ None
+ }
+
+ // https://html.spec.whatwg.org/multipage/#dom-mimetypearray-nameditem
+ fn NamedItem(&self, _name: DOMString) -> Option<Root<MimeType>> {
+ None
+ }
+
+ // https://html.spec.whatwg.org/multipage/#dom-mimetypearray-item
+ fn IndexedGetter(&self, _index: u32, _found: &mut bool) -> Option<Root<MimeType>> {
+ None
+ }
+
+ // check-tidy: no specs after this line
+ fn NamedGetter(&self, _name: DOMString, _found: &mut bool) -> Option<Root<MimeType>> {
+ None
+ }
+
+ // https://heycam.github.io/webidl/#dfn-supported-property-names
+ fn SupportedPropertyNames(&self) -> Vec<DOMString> {
+ vec![]
+ }
+}
diff --git a/components/script/dom/mod.rs b/components/script/dom/mod.rs
index 36921d8be89..853ac520b9a 100644
--- a/components/script/dom/mod.rs
+++ b/components/script/dom/mod.rs
@@ -342,6 +342,8 @@ pub mod imagedata;
pub mod keyboardevent;
pub mod location;
pub mod messageevent;
+pub mod mimetype;
+pub mod mimetypearray;
pub mod mouseevent;
pub mod namednodemap;
pub mod navigator;
@@ -351,6 +353,8 @@ pub mod nodeiterator;
pub mod nodelist;
pub mod performance;
pub mod performancetiming;
+pub mod plugin;
+pub mod pluginarray;
pub mod processinginstruction;
pub mod progressevent;
pub mod radionodelist;
diff --git a/components/script/dom/navigator.rs b/components/script/dom/navigator.rs
index fe01105b787..c1874905a54 100644
--- a/components/script/dom/navigator.rs
+++ b/components/script/dom/navigator.rs
@@ -8,7 +8,9 @@ use dom::bindings::global::GlobalRef;
use dom::bindings::js::{JS, MutNullableHeap, Root};
use dom::bindings::reflector::{Reflector, Reflectable, reflect_dom_object};
use dom::bluetooth::Bluetooth;
+use dom::mimetypearray::MimeTypeArray;
use dom::navigatorinfo;
+use dom::pluginarray::PluginArray;
use dom::window::Window;
use util::str::DOMString;
@@ -16,6 +18,8 @@ use util::str::DOMString;
pub struct Navigator {
reflector_: Reflector,
bluetooth: MutNullableHeap<JS<Bluetooth>>,
+ plugins: MutNullableHeap<JS<PluginArray>>,
+ mime_types: MutNullableHeap<JS<MimeTypeArray>>,
}
impl Navigator {
@@ -23,6 +27,8 @@ impl Navigator {
Navigator {
reflector_: Reflector::new(),
bluetooth: Default::default(),
+ plugins: Default::default(),
+ mime_types: Default::default(),
}
}
@@ -78,4 +84,19 @@ impl NavigatorMethods for Navigator {
fn Language(&self) -> DOMString {
navigatorinfo::Language()
}
+
+ // https://html.spec.whatwg.org/multipage/#dom-navigator-plugins
+ fn Plugins(&self) -> Root<PluginArray> {
+ self.plugins.or_init(|| PluginArray::new(self.global().r()))
+ }
+
+ // https://html.spec.whatwg.org/multipage/#dom-navigator-mimetypes
+ fn MimeTypes(&self) -> Root<MimeTypeArray> {
+ self.mime_types.or_init(|| MimeTypeArray::new(self.global().r()))
+ }
+
+ // https://html.spec.whatwg.org/multipage/#dom-navigator-javaenabled
+ fn JavaEnabled(&self) -> bool {
+ false
+ }
}
diff --git a/components/script/dom/node.rs b/components/script/dom/node.rs
index 748b7b8249e..1e71966e4e7 100644
--- a/components/script/dom/node.rs
+++ b/components/script/dom/node.rs
@@ -594,12 +594,8 @@ impl Node {
let html_element = document.GetDocumentElement();
- let is_body_element = html_element.r().and_then(|root| {
- let node = root.upcast::<Node>();
- node.children().find(|child| { child.is::<HTMLBodyElement>() }).map(|node| {
- *node.r() == *self
- })
- }).unwrap_or(false);
+ let is_body_element = self.downcast::<HTMLBodyElement>()
+ .map_or(false, |e| e.is_the_html_body_element());
let scroll_area = window.scroll_area_query(self.to_trusted_node_address());
diff --git a/components/script/dom/plugin.rs b/components/script/dom/plugin.rs
new file mode 100644
index 00000000000..0836bc32f0f
--- /dev/null
+++ b/components/script/dom/plugin.rs
@@ -0,0 +1,61 @@
+/* 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 http://mozilla.org/MPL/2.0/. */
+
+use dom::bindings::codegen::Bindings::PluginBinding::PluginMethods;
+use dom::bindings::js::Root;
+use dom::bindings::reflector::{Reflector};
+use dom::mimetype::MimeType;
+use util::str::DOMString;
+
+#[dom_struct]
+pub struct Plugin {
+ reflector_: Reflector,
+}
+
+impl PluginMethods for Plugin {
+ // https://html.spec.whatwg.org/multipage/#dom-plugin-name
+ fn Name(&self) -> DOMString {
+ unreachable!()
+ }
+
+ // https://html.spec.whatwg.org/multipage/#dom-plugin-description
+ fn Description(&self) -> DOMString {
+ unreachable!()
+ }
+
+ // https://html.spec.whatwg.org/multipage/#dom-plugin-filename
+ fn Filename(&self) -> DOMString {
+ unreachable!()
+ }
+
+ // https://html.spec.whatwg.org/multipage/#dom-plugin-length
+ fn Length(&self) -> u32 {
+ unreachable!()
+ }
+
+ // https://html.spec.whatwg.org/multipage/#dom-plugin-item
+ fn Item(&self, _index: u32) -> Option<Root<MimeType>> {
+ unreachable!()
+ }
+
+ // https://html.spec.whatwg.org/multipage/#dom-plugin-nameditem
+ fn NamedItem(&self, _name: DOMString) -> Option<Root<MimeType>> {
+ unreachable!()
+ }
+
+ // https://html.spec.whatwg.org/multipage/#dom-plugin-item
+ fn IndexedGetter(&self, _index: u32, _found: &mut bool) -> Option<Root<MimeType>> {
+ unreachable!()
+ }
+
+ // check-tidy: no specs after this line
+ fn NamedGetter(&self, _name: DOMString, _found: &mut bool) -> Option<Root<MimeType>> {
+ unreachable!()
+ }
+
+ // https://heycam.github.io/webidl/#dfn-supported-property-names
+ fn SupportedPropertyNames(&self) -> Vec<DOMString> {
+ unreachable!()
+ }
+}
diff --git a/components/script/dom/pluginarray.rs b/components/script/dom/pluginarray.rs
new file mode 100644
index 00000000000..d94131b1a9f
--- /dev/null
+++ b/components/script/dom/pluginarray.rs
@@ -0,0 +1,67 @@
+/* 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 http://mozilla.org/MPL/2.0/. */
+
+use dom::bindings::codegen::Bindings::PluginArrayBinding;
+use dom::bindings::codegen::Bindings::PluginArrayBinding::PluginArrayMethods;
+use dom::bindings::global::GlobalRef;
+use dom::bindings::js::Root;
+use dom::bindings::reflector::{Reflector, reflect_dom_object};
+use dom::plugin::Plugin;
+use util::str::DOMString;
+
+#[dom_struct]
+pub struct PluginArray {
+ reflector_: Reflector,
+}
+
+impl PluginArray {
+ pub fn new_inherited() -> PluginArray {
+ PluginArray {
+ reflector_: Reflector::new()
+ }
+ }
+
+ pub fn new(global: GlobalRef) -> Root<PluginArray> {
+ reflect_dom_object(box PluginArray::new_inherited(),
+ global,
+ PluginArrayBinding::Wrap)
+ }
+}
+
+impl PluginArrayMethods for PluginArray {
+ // https://html.spec.whatwg.org/multipage/#dom-pluginarray-refresh
+ fn Refresh(&self, _reload: bool) {
+
+ }
+
+ // https://html.spec.whatwg.org/multipage/#dom-pluginarray-length
+ fn Length(&self) -> u32 {
+ 0
+ }
+
+ // https://html.spec.whatwg.org/multipage/#dom-pluginarray-item
+ fn Item(&self, _index: u32) -> Option<Root<Plugin>> {
+ None
+ }
+
+ // https://html.spec.whatwg.org/multipage/#dom-pluginarray-nameditem
+ fn NamedItem(&self, _name: DOMString) -> Option<Root<Plugin>> {
+ None
+ }
+
+ // https://html.spec.whatwg.org/multipage/#dom-pluginarray-item
+ fn IndexedGetter(&self, _index: u32, _found: &mut bool) -> Option<Root<Plugin>> {
+ None
+ }
+
+ // check-tidy: no specs after this line
+ fn NamedGetter(&self, _name: DOMString, _found: &mut bool) -> Option<Root<Plugin>> {
+ None
+ }
+
+ // https://heycam.github.io/webidl/#dfn-supported-property-names
+ fn SupportedPropertyNames(&self) -> Vec<DOMString> {
+ vec![]
+ }
+}
diff --git a/components/script/dom/webglprogram.rs b/components/script/dom/webglprogram.rs
index 996e6eb4cee..d288e9422c4 100644
--- a/components/script/dom/webglprogram.rs
+++ b/components/script/dom/webglprogram.rs
@@ -167,6 +167,17 @@ impl WebGLProgram {
WebGLActiveInfo::new(self.global().r(), size, ty, DOMString::from(name)))
}
+ /// glGetActiveAttrib
+ pub fn get_active_attrib(&self, index: u32) -> WebGLResult<Root<WebGLActiveInfo>> {
+ let (sender, receiver) = ipc::channel().unwrap();
+ self.renderer
+ .send(CanvasMsg::WebGL(WebGLCommand::GetActiveAttrib(self.id, index, sender)))
+ .unwrap();
+
+ receiver.recv().unwrap().map(|(size, ty, name)|
+ WebGLActiveInfo::new(self.global().r(), size, ty, DOMString::from(name)))
+ }
+
/// glGetAttribLocation
pub fn get_attrib_location(&self, name: DOMString) -> WebGLResult<Option<i32>> {
if name.len() > MAX_UNIFORM_AND_ATTRIBUTE_LEN {
diff --git a/components/script/dom/webglrenderingcontext.rs b/components/script/dom/webglrenderingcontext.rs
index 920fd91bbad..4c6996cbb90 100644
--- a/components/script/dom/webglrenderingcontext.rs
+++ b/components/script/dom/webglrenderingcontext.rs
@@ -31,7 +31,7 @@ use js::jsapi::{JSContext, JSObject, RootedValue};
use js::jsval::{BooleanValue, DoubleValue, Int32Value, JSVal, NullValue, UndefinedValue};
use net_traits::image::base::PixelFormat;
use net_traits::image_cache_thread::ImageResponse;
-use offscreen_gl_context::GLContextAttributes;
+use offscreen_gl_context::{GLContextAttributes, GLLimits};
use script_traits::ScriptMsg as ConstellationMsg;
use std::cell::Cell;
use util::str::DOMString;
@@ -71,6 +71,8 @@ pub struct WebGLRenderingContext {
reflector_: Reflector,
#[ignore_heap_size_of = "Defined in ipc-channel"]
ipc_renderer: IpcSender<CanvasMsg>,
+ #[ignore_heap_size_of = "Defined in offscreen_gl_context"]
+ limits: GLLimits,
canvas: JS<HTMLCanvasElement>,
#[ignore_heap_size_of = "Defined in webrender_traits"]
last_error: Cell<Option<WebGLError>>,
@@ -95,10 +97,11 @@ impl WebGLRenderingContext {
.unwrap();
let result = receiver.recv().unwrap();
- result.map(|ipc_renderer| {
+ result.map(|(ipc_renderer, context_limits)| {
WebGLRenderingContext {
reflector_: Reflector::new(),
ipc_renderer: ipc_renderer,
+ limits: context_limits,
canvas: JS::from_ref(canvas),
last_error: Cell::new(None),
texture_unpacking_settings: Cell::new(CONVERT_COLORSPACE),
@@ -139,6 +142,9 @@ impl WebGLRenderingContext {
}
pub fn webgl_error(&self, err: WebGLError) {
+ // TODO(emilio): Add useful debug messages to this
+ warn!("WebGL error: {:?}, previous error was {:?}", err, self.last_error.get());
+
// If an error has been detected no further errors must be
// recorded until `getError` has been called
if self.last_error.get().is_none() {
@@ -155,7 +161,7 @@ impl WebGLRenderingContext {
if let Some(texture) = texture {
handle_potential_webgl_error!(self, texture.tex_parameter(target, name, value));
} else {
- return self.webgl_error(InvalidOperation);
+ self.webgl_error(InvalidOperation)
}
}
@@ -164,6 +170,10 @@ impl WebGLRenderingContext {
}
fn vertex_attrib(&self, indx: u32, x: f32, y: f32, z: f32, w: f32) {
+ if indx > self.limits.max_vertex_attribs {
+ return self.webgl_error(InvalidValue);
+ }
+
self.ipc_renderer
.send(CanvasMsg::WebGL(WebGLCommand::VertexAttrib(indx, x, y, z, w)))
.unwrap();
@@ -680,6 +690,13 @@ impl WebGLRenderingContextMethods for WebGLRenderingContext {
// https://www.khronos.org/registry/webgl/specs/latest/1.0/#5.14.9
fn CreateShader(&self, shader_type: u32) -> Option<Root<WebGLShader>> {
+ match shader_type {
+ constants::VERTEX_SHADER | constants::FRAGMENT_SHADER => {},
+ _ => {
+ self.webgl_error(InvalidEnum);
+ return None;
+ }
+ }
WebGLShader::maybe_new(self.global().r(), self.ipc_renderer.clone(), shader_type)
}
@@ -737,13 +754,13 @@ impl WebGLRenderingContextMethods for WebGLRenderingContext {
}
if first < 0 || count < 0 {
- self.webgl_error(InvalidValue);
- } else {
- self.ipc_renderer
- .send(CanvasMsg::WebGL(WebGLCommand::DrawArrays(mode, first, count)))
- .unwrap();
- self.mark_as_dirty();
+ return self.webgl_error(InvalidValue);
}
+
+ self.ipc_renderer
+ .send(CanvasMsg::WebGL(WebGLCommand::DrawArrays(mode, first, count)))
+ .unwrap();
+ self.mark_as_dirty();
},
_ => self.webgl_error(InvalidEnum),
}
@@ -790,6 +807,10 @@ impl WebGLRenderingContextMethods for WebGLRenderingContext {
// https://www.khronos.org/registry/webgl/specs/latest/1.0/#5.14.10
fn EnableVertexAttribArray(&self, attrib_id: u32) {
+ if attrib_id > self.limits.max_vertex_attribs {
+ return self.webgl_error(InvalidValue);
+ }
+
self.ipc_renderer
.send(CanvasMsg::WebGL(WebGLCommand::EnableVertexAttribArray(attrib_id)))
.unwrap()
@@ -807,6 +828,17 @@ impl WebGLRenderingContextMethods for WebGLRenderingContext {
}
// https://www.khronos.org/registry/webgl/specs/latest/1.0/#5.14.10
+ fn GetActiveAttrib(&self, program: Option<&WebGLProgram>, index: u32) -> Option<Root<WebGLActiveInfo>> {
+ program.and_then(|p| match p.get_active_attrib(index) {
+ Ok(ret) => Some(ret),
+ Err(error) => {
+ self.webgl_error(error);
+ None
+ },
+ })
+ }
+
+ // https://www.khronos.org/registry/webgl/specs/latest/1.0/#5.14.10
fn GetAttribLocation(&self, program: Option<&WebGLProgram>, name: DOMString) -> i32 {
if let Some(program) = program {
handle_potential_webgl_error!(self, program.get_attrib_location(name), None).unwrap_or(-1)
@@ -1188,7 +1220,6 @@ impl WebGLRenderingContextMethods for WebGLRenderingContext {
self.vertex_attrib(indx, x, 0f32, 0f32, 1f32)
}
- #[allow(unsafe_code)]
// https://www.khronos.org/registry/webgl/specs/latest/1.0/#5.14.10
fn VertexAttrib1fv(&self, _cx: *mut JSContext, indx: u32, data: *mut JSObject) {
if let Some(data_vec) = array_buffer_view_to_vec_checked::<f32>(data) {
@@ -1206,7 +1237,6 @@ impl WebGLRenderingContextMethods for WebGLRenderingContext {
self.vertex_attrib(indx, x, y, 0f32, 1f32)
}
- #[allow(unsafe_code)]
// https://www.khronos.org/registry/webgl/specs/latest/1.0/#5.14.10
fn VertexAttrib2fv(&self, _cx: *mut JSContext, indx: u32, data: *mut JSObject) {
if let Some(data_vec) = array_buffer_view_to_vec_checked::<f32>(data) {
@@ -1257,6 +1287,10 @@ impl WebGLRenderingContextMethods for WebGLRenderingContext {
// https://www.khronos.org/registry/webgl/specs/latest/1.0/#5.14.10
fn VertexAttribPointer(&self, attrib_id: u32, size: i32, data_type: u32,
normalized: bool, stride: i32, offset: i64) {
+ if attrib_id > self.limits.max_vertex_attribs {
+ return self.webgl_error(InvalidValue);
+ }
+
if let constants::FLOAT = data_type {
let msg = CanvasMsg::WebGL(
WebGLCommand::VertexAttribPointer2f(attrib_id, size, normalized, stride, offset as u32));
diff --git a/components/script/dom/webglshader.rs b/components/script/dom/webglshader.rs
index 804dc3cdcf8..495417065d7 100644
--- a/components/script/dom/webglshader.rs
+++ b/components/script/dom/webglshader.rs
@@ -101,6 +101,7 @@ impl WebGLShader {
&BuiltInResources::default()).unwrap();
match validator.compile_and_translate(&[source]) {
Ok(translated_source) => {
+ debug!("Shader translated: {}", translated_source);
// NOTE: At this point we should be pretty sure that the compilation in the paint thread
// will succeed.
// It could be interesting to retrieve the info log from the paint thread though
diff --git a/components/script/dom/webidls/CSSStyleDeclaration.webidl b/components/script/dom/webidls/CSSStyleDeclaration.webidl
index dba69a515b0..10cf77ccc83 100644
--- a/components/script/dom/webidls/CSSStyleDeclaration.webidl
+++ b/components/script/dom/webidls/CSSStyleDeclaration.webidl
@@ -310,4 +310,5 @@ partial interface CSSStyleDeclaration {
[SetterThrows, TreatNullAs=EmptyString] attribute DOMString flexDirection;
[SetterThrows, TreatNullAs=EmptyString] attribute DOMString flex-direction;
+ [SetterThrows, TreatNullAs=EmptyString] attribute DOMString order;
};
diff --git a/components/script/dom/webidls/HTMLHRElement.webidl b/components/script/dom/webidls/HTMLHRElement.webidl
index f203527b2bf..e3ba6113748 100644
--- a/components/script/dom/webidls/HTMLHRElement.webidl
+++ b/components/script/dom/webidls/HTMLHRElement.webidl
@@ -10,7 +10,7 @@ interface HTMLHRElement : HTMLElement {
// https://html.spec.whatwg.org/multipage/#HTMLHRElement-partial
partial interface HTMLHRElement {
- // attribute DOMString align;
+ attribute DOMString align;
attribute DOMString color;
// attribute boolean noShade;
// attribute DOMString size;
diff --git a/components/script/dom/webidls/HTMLInputElement.webidl b/components/script/dom/webidls/HTMLInputElement.webidl
index 2e1c6215f2b..66907c5cd23 100644
--- a/components/script/dom/webidls/HTMLInputElement.webidl
+++ b/components/script/dom/webidls/HTMLInputElement.webidl
@@ -5,13 +5,13 @@
// https://html.spec.whatwg.org/multipage/#htmlinputelement
interface HTMLInputElement : HTMLElement {
- // attribute DOMString accept;
- // attribute DOMString alt;
+ attribute DOMString accept;
+ attribute DOMString alt;
// attribute DOMString autocomplete;
// attribute boolean autofocus;
attribute boolean defaultChecked;
attribute boolean checked;
- // attribute DOMString dirName;
+ attribute DOMString dirName;
attribute boolean disabled;
readonly attribute HTMLFormElement? form;
//readonly attribute FileList? files;
@@ -24,21 +24,21 @@ interface HTMLInputElement : HTMLElement {
attribute boolean indeterminate;
// attribute DOMString inputMode;
//readonly attribute HTMLElement? list;
- // attribute DOMString max;
+ attribute DOMString max;
[SetterThrows]
attribute long maxLength;
- // attribute DOMString min;
+ attribute DOMString min;
// attribute long minLength;
- // attribute boolean multiple;
+ attribute boolean multiple;
attribute DOMString name;
- // attribute DOMString pattern;
+ attribute DOMString pattern;
attribute DOMString placeholder;
attribute boolean readOnly;
- // attribute boolean required;
+ attribute boolean required;
[SetterThrows]
attribute unsigned long size;
- // attribute DOMString src;
- // attribute DOMString step;
+ attribute DOMString src;
+ attribute DOMString step;
attribute DOMString type;
attribute DOMString defaultValue;
[TreatNullAs=EmptyString, SetterThrows]
diff --git a/components/script/dom/webidls/MimeType.webidl b/components/script/dom/webidls/MimeType.webidl
new file mode 100644
index 00000000000..9972134f7c8
--- /dev/null
+++ b/components/script/dom/webidls/MimeType.webidl
@@ -0,0 +1,12 @@
+/* -*- Mode: IDL; tab-width: 2; indent-tabs-mode: nil; c-basic-offset: 2 -*- */
+/* 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 http://mozilla.org/MPL/2.0/. */
+
+// https://html.spec.whatwg.org/multipage/#mimetype
+interface MimeType {
+ readonly attribute DOMString type;
+ readonly attribute DOMString description;
+ readonly attribute DOMString suffixes; // comma-separated
+ readonly attribute Plugin enabledPlugin;
+};
diff --git a/components/script/dom/webidls/MimeTypeArray.webidl b/components/script/dom/webidls/MimeTypeArray.webidl
new file mode 100644
index 00000000000..6a4d8f1aa4e
--- /dev/null
+++ b/components/script/dom/webidls/MimeTypeArray.webidl
@@ -0,0 +1,12 @@
+/* -*- Mode: IDL; tab-width: 2; indent-tabs-mode: nil; c-basic-offset: 2 -*- */
+/* 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 http://mozilla.org/MPL/2.0/. */
+
+// https://html.spec.whatwg.org/multipage/#mimetypearray
+[LegacyUnenumerableNamedProperties]
+interface MimeTypeArray {
+ readonly attribute unsigned long length;
+ getter MimeType? item(unsigned long index);
+ getter MimeType? namedItem(DOMString name);
+};
diff --git a/components/script/dom/webidls/Navigator.webidl b/components/script/dom/webidls/Navigator.webidl
index 50f695279ff..b793af7a6f5 100644
--- a/components/script/dom/webidls/Navigator.webidl
+++ b/components/script/dom/webidls/Navigator.webidl
@@ -13,7 +13,7 @@ Navigator implements NavigatorLanguage;
//Navigator implements NavigatorOnLine;
//Navigator implements NavigatorContentUtils;
//Navigator implements NavigatorStorageUtils;
-//Navigator implements NavigatorPlugins;
+Navigator implements NavigatorPlugins;
// https://html.spec.whatwg.org/multipage/#navigatorid
[NoInterfaceObject/*, Exposed=Window,Worker*/]
@@ -39,3 +39,11 @@ interface NavigatorLanguage {
// https://github.com/servo/servo/issues/10073
//readonly attribute DOMString[] languages;
};
+
+// https://html.spec.whatwg.org/multipage/#navigatorplugins
+[NoInterfaceObject]
+interface NavigatorPlugins {
+ [SameObject] readonly attribute PluginArray plugins;
+ [SameObject] readonly attribute MimeTypeArray mimeTypes;
+ boolean javaEnabled();
+};
diff --git a/components/script/dom/webidls/Plugin.webidl b/components/script/dom/webidls/Plugin.webidl
new file mode 100644
index 00000000000..4fb172d45b9
--- /dev/null
+++ b/components/script/dom/webidls/Plugin.webidl
@@ -0,0 +1,15 @@
+/* -*- Mode: IDL; tab-width: 2; indent-tabs-mode: nil; c-basic-offset: 2 -*- */
+/* 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 http://mozilla.org/MPL/2.0/. */
+
+// https://html.spec.whatwg.org/multipage/#dom-plugin
+[LegacyUnenumerableNamedProperties]
+interface Plugin {
+ readonly attribute DOMString name;
+ readonly attribute DOMString description;
+ readonly attribute DOMString filename;
+ readonly attribute unsigned long length;
+ getter MimeType? item(unsigned long index);
+ getter MimeType? namedItem(DOMString name);
+};
diff --git a/components/script/dom/webidls/PluginArray.webidl b/components/script/dom/webidls/PluginArray.webidl
new file mode 100644
index 00000000000..f2fde35fc4f
--- /dev/null
+++ b/components/script/dom/webidls/PluginArray.webidl
@@ -0,0 +1,13 @@
+/* -*- Mode: IDL; tab-width: 2; indent-tabs-mode: nil; c-basic-offset: 2 -*- */
+/* 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 http://mozilla.org/MPL/2.0/. */
+
+// https://html.spec.whatwg.org/multipage/#pluginarray
+[LegacyUnenumerableNamedProperties]
+interface PluginArray {
+ void refresh(optional boolean reload = false);
+ readonly attribute unsigned long length;
+ getter Plugin? item(unsigned long index);
+ getter Plugin? namedItem(DOMString name);
+};
diff --git a/components/script/dom/webidls/WebGLRenderingContext.webidl b/components/script/dom/webidls/WebGLRenderingContext.webidl
index 7be7a82d41e..d2c93d9a3c5 100644
--- a/components/script/dom/webidls/WebGLRenderingContext.webidl
+++ b/components/script/dom/webidls/WebGLRenderingContext.webidl
@@ -567,7 +567,7 @@ interface WebGLRenderingContextBase
void generateMipmap(GLenum target);
- //WebGLActiveInfo? getActiveAttrib(WebGLProgram? program, GLuint index);
+ WebGLActiveInfo? getActiveAttrib(WebGLProgram? program, GLuint index);
WebGLActiveInfo? getActiveUniform(WebGLProgram? program, GLuint index);
//sequence<WebGLShader>? getAttachedShaders(WebGLProgram? program);
diff --git a/components/script/dom/xmlhttprequest.rs b/components/script/dom/xmlhttprequest.rs
index ab8f8f96413..1d7c2bffd34 100644
--- a/components/script/dom/xmlhttprequest.rs
+++ b/components/script/dom/xmlhttprequest.rs
@@ -350,7 +350,7 @@ impl XMLHttpRequestMethods for XMLHttpRequest {
}
// Step 2
- let base = self.global().r().get_url();
+ let base = self.global().r().api_base_url();
// Step 6
let mut parsed_url = match base.join(&url.0) {
Ok(parsed) => parsed,
diff --git a/components/script/script_runtime.rs b/components/script/script_runtime.rs
index 509a7e93e71..6147fc8bd2b 100644
--- a/components/script/script_runtime.rs
+++ b/components/script/script_runtime.rs
@@ -13,6 +13,8 @@ use js::glue::CollectServoSizes;
use js::jsapi::{DisableIncrementalGC, GCDescription, GCProgress};
use js::jsapi::{JSContext, JS_GetRuntime, JSRuntime, JSTracer, SetDOMCallbacks, SetGCSliceCallback};
use js::jsapi::{JSGCInvocationKind, JSGCStatus, JS_AddExtraGCRootsTracer, JS_SetGCCallback};
+use js::jsapi::{JSGCMode, JSGCParamKey, JS_SetGCParameter, JS_SetGlobalJitCompilerOption};
+use js::jsapi::{JSJitCompilerOption, JS_SetOffthreadIonCompilationEnabled, JS_SetParallelParsingEnabled};
use js::jsapi::{JSObject, RuntimeOptionsRef, SetPreserveWrapperCallback};
use js::rust::Runtime;
use libc;
@@ -130,6 +132,181 @@ pub fn new_rt_and_cx() -> Runtime {
if let Some(val) = get_pref("js.ion.enabled").as_boolean() {
rt_opts.set_ion_(val);
}
+ if let Some(val) = get_pref("js.asmjs.enabled").as_boolean() {
+ rt_opts.set_asmJS_(val);
+ }
+ if let Some(val) = get_pref("js.strict.enabled").as_boolean() {
+ rt_opts.set_extraWarnings_(val);
+ }
+ // TODO: handle js.strict.debug.enabled
+ // TODO: handle js.throw_on_asmjs_validation_failure (needs new Spidermonkey)
+ if let Some(val) = get_pref("js.native_regexp.enabled").as_boolean() {
+ rt_opts.set_nativeRegExp_(val);
+ }
+ if let Some(val) = get_pref("js.parallel_parsing.enabled").as_boolean() {
+ unsafe { JS_SetParallelParsingEnabled(runtime.rt(), val); }
+ }
+ if let Some(val) = get_pref("js.offthread_compilation_enabled").as_boolean() {
+ unsafe { JS_SetOffthreadIonCompilationEnabled(runtime.rt(), val); }
+ }
+ if let Some(val) = get_pref("js.baseline.unsafe_eager_compilation.enabled").as_boolean() {
+ let trigger: i32 = if val {
+ 0
+ } else {
+ -1
+ };
+ unsafe {
+ JS_SetGlobalJitCompilerOption(runtime.rt(),
+ JSJitCompilerOption::JSJITCOMPILER_BASELINE_WARMUP_TRIGGER,
+ trigger as u32);
+ }
+ }
+ if let Some(val) = get_pref("js.ion.unsafe_eager_compilation.enabled").as_boolean() {
+ let trigger: i64 = if val {
+ 0
+ } else {
+ -1
+ };
+ unsafe {
+ JS_SetGlobalJitCompilerOption(runtime.rt(),
+ JSJitCompilerOption::JSJITCOMPILER_ION_WARMUP_TRIGGER,
+ trigger as u32);
+ }
+ }
+ // TODO: handle js.discard_system_source.enabled
+ // TODO: handle js.asyncstack.enabled (needs new Spidermonkey)
+ // TODO: handle js.throw_on_debugee_would_run (needs new Spidermonkey)
+ // TODO: handle js.dump_stack_on_debugee_would_run (needs new Spidermonkey)
+ if let Some(val) = get_pref("js.werror.enabled").as_boolean() {
+ rt_opts.set_werror_(val);
+ }
+ // TODO: handle js.shared_memory.enabled
+ if let Some(val) = get_pref("js.mem.high_water_mark").as_i64() {
+ unsafe {
+ JS_SetGCParameter(runtime.rt(), JSGCParamKey::JSGC_MAX_MALLOC_BYTES, val as u32 * 1024 * 1024);
+ }
+ }
+ if let Some(val) = get_pref("js.mem.max").as_i64() {
+ let max = if val <= 0 || val >= 0x1000 {
+ -1
+ } else {
+ val * 1024 * 1024
+ };
+ unsafe {
+ JS_SetGCParameter(runtime.rt(), JSGCParamKey::JSGC_MAX_BYTES, max as u32);
+ }
+ }
+ // NOTE: This is disabled above, so enabling it here will do nothing for now.
+ if let Some(val) = get_pref("js.mem.gc.incremental.enabled").as_boolean() {
+ let compartment = if let Some(val) = get_pref("js.mem.gc.per_compartment.enabled").as_boolean() {
+ val
+ } else {
+ false
+ };
+ let mode = if val {
+ JSGCMode::JSGC_MODE_INCREMENTAL
+ } else if compartment {
+ JSGCMode::JSGC_MODE_COMPARTMENT
+ } else {
+ JSGCMode::JSGC_MODE_GLOBAL
+ };
+ unsafe {
+ JS_SetGCParameter(runtime.rt(), JSGCParamKey::JSGC_MODE, mode as u32);
+ }
+ }
+ if let Some(val) = get_pref("js.mem.gc.incremental.slice_ms").as_i64() {
+ if val >= 0 && val < 100000 {
+ unsafe {
+ JS_SetGCParameter(runtime.rt(), JSGCParamKey::JSGC_SLICE_TIME_BUDGET, val as u32);
+ }
+ }
+ }
+ if let Some(val) = get_pref("js.mem.gc.compacting.enabled").as_boolean() {
+ unsafe {
+ JS_SetGCParameter(runtime.rt(), JSGCParamKey::JSGC_COMPACTING_ENABLED, val as u32);
+ }
+ }
+ if let Some(val) = get_pref("js.mem.gc.high_frequency_time_limit_ms").as_i64() {
+ if val >= 0 && val < 10000 {
+ unsafe {
+ JS_SetGCParameter(runtime.rt(), JSGCParamKey::JSGC_HIGH_FREQUENCY_TIME_LIMIT, val as u32);
+ }
+ }
+ }
+ if let Some(val) = get_pref("js.mem.gc.dynamic_mark_slice.enabled").as_boolean() {
+ unsafe {
+ JS_SetGCParameter(runtime.rt(), JSGCParamKey::JSGC_DYNAMIC_MARK_SLICE, val as u32);
+ }
+ }
+ // TODO: handle js.mem.gc.refresh_frame_slices.enabled
+ if let Some(val) = get_pref("js.mem.gc.dynamic_heap_growth.enabled").as_boolean() {
+ unsafe {
+ JS_SetGCParameter(runtime.rt(), JSGCParamKey::JSGC_DYNAMIC_HEAP_GROWTH, val as u32);
+ }
+ }
+ if let Some(val) = get_pref("js.mem.gc.low_frequency_heap_growth").as_i64() {
+ if val >= 0 && val < 10000 {
+ unsafe {
+ JS_SetGCParameter(runtime.rt(), JSGCParamKey::JSGC_LOW_FREQUENCY_HEAP_GROWTH, val as u32);
+ }
+ }
+ }
+ if let Some(val) = get_pref("js.mem.gc.high_frequency_heap_growth_min").as_i64() {
+ if val >= 0 && val < 10000 {
+ unsafe {
+ JS_SetGCParameter(runtime.rt(), JSGCParamKey::JSGC_HIGH_FREQUENCY_HEAP_GROWTH_MIN, val as u32);
+ }
+ }
+ }
+ if let Some(val) = get_pref("js.mem.gc.high_frequency_heap_growth_max").as_i64() {
+ if val >= 0 && val < 10000 {
+ unsafe {
+ JS_SetGCParameter(runtime.rt(), JSGCParamKey::JSGC_HIGH_FREQUENCY_HEAP_GROWTH_MAX, val as u32);
+ }
+ }
+ }
+ if let Some(val) = get_pref("js.mem.gc.high_frequency_low_limit_mb").as_i64() {
+ if val >= 0 && val < 10000 {
+ unsafe {
+ JS_SetGCParameter(runtime.rt(), JSGCParamKey::JSGC_HIGH_FREQUENCY_LOW_LIMIT, val as u32);
+ }
+ }
+ }
+ if let Some(val) = get_pref("js.mem.gc.high_frequency_high_limit_mb").as_i64() {
+ if val >= 0 && val < 10000 {
+ unsafe {
+ JS_SetGCParameter(runtime.rt(), JSGCParamKey::JSGC_HIGH_FREQUENCY_HIGH_LIMIT, val as u32);
+ }
+ }
+ }
+ if let Some(val) = get_pref("js.mem.gc.allocation_threshold_mb").as_i64() {
+ if val >= 0 && val < 10000 {
+ unsafe {
+ JS_SetGCParameter(runtime.rt(), JSGCParamKey::JSGC_ALLOCATION_THRESHOLD, val as u32);
+ }
+ }
+ }
+ if let Some(val) = get_pref("js.mem.gc.decommit_threshold_mb").as_i64() {
+ if val >= 0 && val < 10000 {
+ unsafe {
+ JS_SetGCParameter(runtime.rt(), JSGCParamKey::JSGC_DECOMMIT_THRESHOLD, val as u32);
+ }
+ }
+ }
+ if let Some(val) = get_pref("js.mem.gc.empty_chunk_count_min").as_i64() {
+ if val >= 0 && val < 10000 {
+ unsafe {
+ JS_SetGCParameter(runtime.rt(), JSGCParamKey::JSGC_MIN_EMPTY_CHUNK_COUNT, val as u32);
+ }
+ }
+ }
+ if let Some(val) = get_pref("js.mem.gc.empty_chunk_count_max").as_i64() {
+ if val >= 0 && val < 10000 {
+ unsafe {
+ JS_SetGCParameter(runtime.rt(), JSGCParamKey::JSGC_MAX_EMPTY_CHUNK_COUNT, val as u32);
+ }
+ }
+ }
runtime
}
diff --git a/components/script/script_thread.rs b/components/script/script_thread.rs
index b9027c96390..7cb24e110bc 100644
--- a/components/script/script_thread.rs
+++ b/components/script/script_thread.rs
@@ -52,7 +52,8 @@ use hyper::mime::{Mime, SubLevel, TopLevel};
use ipc_channel::ipc::{self, IpcSender};
use ipc_channel::router::ROUTER;
use js::jsapi::{DOMProxyShadowsResult, HandleId, HandleObject, RootedValue};
-use js::jsapi::{JSAutoRequest, JSContext, JS_SetWrapObjectCallbacks, JSTracer};
+use js::jsapi::{JSAutoRequest, JS_SetWrapObjectCallbacks};
+use js::jsapi::{JSContext, JSTracer};
use js::jsval::UndefinedValue;
use js::rust::Runtime;
use layout_interface::{ReflowQueryType};