Auto merge of #13786 - heycam:background-image, r=Manishearth

support url() values in background-image, mask-image and list-style-image in stylo

<!-- Please describe your changes on the following line: -->
Corresponding Gecko bugs, where @Manishearth has given r+s:

* https://bugzilla.mozilla.org/show_bug.cgi?id=1288302
* https://bugzilla.mozilla.org/show_bug.cgi?id=1310463

(Sorry for the large structs_{debug,release}.rs changes; I thought it was too much trouble to disentangle the useless changes from the legitimate ones.)

Holding off on landing this until the Gecko patches are reviewed and landed.

---
<!-- Thank you for contributing to Servo! Please replace each `[ ]` by `[X]` when the step is complete, and replace `__` with appropriate data: -->
- [X] `./mach build -d` does not report any errors
- [X] `./mach test-tidy` does not report any errors
- [ ] These changes fix #__ (github issue number if applicable).

<!-- Either: -->
- [ ] There are tests for these changes OR
- [X] These changes do not require tests because I've tested the stylo functionality manually and we can rely on Gecko's existing tests going forward

<!-- Pull requests that do not address these steps are welcome, but they will require additional verification as part of the review process. -->

<!-- Reviewable:start -->
---
This change is [<img src="https://reviewable.io/review_button.svg" height="34" align="absmiddle" alt="Reviewable"/>](https://reviewable.io/reviews/servo/servo/13786)
<!-- Reviewable:end -->
This commit is contained in:
bors-servo 2016-10-28 07:16:30 -05:00 committed by GitHub
commit a27d54e07f
9 changed files with 1914 additions and 2021 deletions

View file

@ -67,7 +67,8 @@ class Longhand(object):
def __init__(self, style_struct, name, animatable=None, derived_from=None, keyword=None,
predefined_type=None, custom_cascade=False, experimental=False, internal=False,
need_clone=False, need_index=False, gecko_ffi_name=None, depend_on_viewport_size=False,
allowed_in_keyframe_block=True, complex_color=False, cast_type='u8'):
allowed_in_keyframe_block=True, complex_color=False, cast_type='u8',
has_uncacheable_values=False):
self.name = name
self.keyword = keyword
self.predefined_type = predefined_type
@ -78,6 +79,7 @@ class Longhand(object):
self.custom_cascade = custom_cascade
self.internal = internal
self.need_index = need_index
self.has_uncacheable_values = has_uncacheable_values
self.gecko_ffi_name = gecko_ffi_name or "m" + self.camel_case
self.depend_on_viewport_size = depend_on_viewport_size
self.derived_from = (derived_from or "").split()

View file

@ -19,6 +19,7 @@ use gecko_bindings::bindings::Gecko_Destroy_${style_struct.gecko_ffi_name};
% endfor
use gecko_bindings::bindings::Gecko_CopyFontFamilyFrom;
use gecko_bindings::bindings::Gecko_CopyImageValueFrom;
use gecko_bindings::bindings::Gecko_CopyListStyleImageFrom;
use gecko_bindings::bindings::Gecko_CopyListStyleTypeFrom;
use gecko_bindings::bindings::Gecko_CopyMozBindingFrom;
use gecko_bindings::bindings::Gecko_CreateGradient;
@ -27,9 +28,12 @@ use gecko_bindings::bindings::Gecko_FontFamilyList_AppendGeneric;
use gecko_bindings::bindings::Gecko_FontFamilyList_AppendNamed;
use gecko_bindings::bindings::Gecko_FontFamilyList_Clear;
use gecko_bindings::bindings::Gecko_SetGradientImageValue;
use gecko_bindings::bindings::Gecko_SetListStyleImage;
use gecko_bindings::bindings::Gecko_SetListStyleImageNone;
use gecko_bindings::bindings::Gecko_SetListStyleType;
use gecko_bindings::bindings::Gecko_SetMozBinding;
use gecko_bindings::bindings::Gecko_SetNullImageValue;
use gecko_bindings::bindings::Gecko_SetUrlImageValue;
use gecko_bindings::bindings::ServoComputedValuesBorrowedOrNull;
use gecko_bindings::bindings::{Gecko_ResetFilters, Gecko_CopyFiltersFrom};
use gecko_bindings::structs;
@ -471,8 +475,7 @@ impl Debug for ${style_struct.gecko_struct_name} {
# These are part of shorthands so we must include them in stylo builds,
# but we haven't implemented the stylo glue for the longhand
# so we generate a stub
force_stub += ["list-style-image", # box
"flex-basis", # position
force_stub += ["flex-basis", # position
# transition
"transition-duration", "transition-timing-function",
@ -1212,8 +1215,10 @@ fn static_assert() {
}
}
#[allow(unused_variables)]
pub fn set_${shorthand}_image(&mut self,
images: longhands::${shorthand}_image::computed_value::T) {
images: longhands::${shorthand}_image::computed_value::T,
cacheable: &mut bool) {
use gecko_bindings::structs::nsStyleImage;
use gecko_bindings::structs::nsStyleImageLayers_LayerType as LayerType;
use gecko_bindings::structs::{NS_STYLE_GRADIENT_SHAPE_LINEAR, NS_STYLE_GRADIENT_SHAPE_CIRCULAR};
@ -1401,13 +1406,20 @@ fn static_assert() {
Image::Gradient(gradient) => {
set_gradient(gradient, &mut geckoimage.mImage)
},
Image::Url(..) => {
// let utf8_bytes = url.as_bytes();
// Gecko_SetUrlImageValue(&mut self.gecko.mImage.mLayers.mFirstElement,
// utf8_bytes.as_ptr() as *const _,
// utf8_bytes.len());
warn!("stylo: imgRequestProxies are not threadsafe in gecko, \
background-image: url() not yet implemented");
Image::Url(ref url, ref extra_data) => {
unsafe {
Gecko_SetUrlImageValue(&mut geckoimage.mImage,
url.as_str().as_ptr(),
url.as_str().len() as u32,
extra_data.base.get(),
extra_data.referrer.get(),
extra_data.principal.get());
}
// We unfortunately must make any url() value uncacheable, since
// the applicable declarations cache is not per document, but
// global, and the imgRequestProxy objects we store in the style
// structs don't like to be tracked by more than one document.
*cacheable = false;
}
}
}
@ -1477,10 +1489,42 @@ fn static_assert() {
</%self:simple_image_array_property>
</%self:impl_trait>
<%self:impl_trait style_struct_name="List" skip_longhands="list-style-type quotes" skip_additionals="*">
<%self:impl_trait style_struct_name="List"
skip_longhands="list-style-image list-style-type quotes"
skip_additionals="*">
pub fn set_list_style_image(&mut self, image: longhands::list_style_image::computed_value::T) {
use values::computed::UrlOrNone;
match image {
UrlOrNone::None => {
unsafe {
Gecko_SetListStyleImageNone(&mut self.gecko);
}
}
UrlOrNone::Url(ref url, ref extra_data) => {
unsafe {
Gecko_SetListStyleImage(&mut self.gecko,
url.as_str().as_ptr(),
url.as_str().len() as u32,
extra_data.base.get(),
extra_data.referrer.get(),
extra_data.principal.get());
}
// We don't need to record this struct as uncacheable, like when setting
// background-image to a url() value, since only properties in reset structs
// are re-used from the applicable declaration cache, and the List struct
// is an inherited struct.
}
}
}
pub fn copy_list_style_image_from(&mut self, other: &Self) {
unsafe { Gecko_CopyListStyleImageFrom(&mut self.gecko, &other.gecko); }
}
${impl_keyword_setter("list_style_type", "__LIST_STYLE_TYPE__",
data.longhands_by_name["list-style-type"].keyword)}
pub fn copy_list_style_type_from(&mut self, other: &Self) {
unsafe {
Gecko_CopyListStyleTypeFrom(&mut self.gecko, &other.gecko);

View file

@ -224,8 +224,13 @@
match *value {
DeclaredValue::Value(ref specified_value) => {
let computed = specified_value.to_computed_value(context);
% if property.has_uncacheable_values:
context.mutate_style().mutate_${data.current_style_struct.name_lower}()
.set_${property.ident}(computed, cacheable);
% else:
context.mutate_style().mutate_${data.current_style_struct.name_lower}()
.set_${property.ident}(computed);
% endif
}
DeclaredValue::WithVariables { .. } => unreachable!(),
DeclaredValue::Initial => {

View file

@ -10,7 +10,8 @@ ${helpers.predefined_type("background-color", "CSSColor",
"::cssparser::Color::RGBA(::cssparser::RGBA { red: 0., green: 0., blue: 0., alpha: 0. }) /* transparent */",
animatable=True)}
<%helpers:vector_longhand name="background-image" animatable="False">
<%helpers:vector_longhand name="background-image" animatable="False"
has_uncacheable_values="${product == 'gecko'}">
use cssparser::ToCss;
use std::fmt;
use values::specified::Image;

View file

@ -146,7 +146,8 @@ ${helpers.single_keyword("mask-composite",
products="gecko",
animatable=False)}
<%helpers:vector_longhand name="mask-image" products="gecko" animatable="False">
<%helpers:vector_longhand name="mask-image" products="gecko" animatable="False"
has_uncacheable_values="${product == 'gecko'}">
use cssparser::ToCss;
use std::fmt;
use url::Url;