mirror of
https://github.com/servo/servo.git
synced 2025-06-06 16:45:39 +00:00
Store resolved font style in canvas context state
This commit is contained in:
parent
5493424d9a
commit
15fd256302
11 changed files with 81 additions and 49 deletions
|
@ -40,9 +40,10 @@ use style::computed_values::visibility::T as Visibility;
|
|||
use style::context::{QuirksMode, SharedStyleContext, StyleContext, ThreadLocalStyleContext};
|
||||
use style::dom::TElement;
|
||||
use style::logical_geometry::{BlockFlowDirection, InlineBaseDirection, WritingMode};
|
||||
use style::properties::style_structs::{self, Font};
|
||||
use style::properties::{
|
||||
parse_one_declaration_into, style_structs, ComputedValues, Importance, LonghandId,
|
||||
PropertyDeclarationBlock, PropertyDeclarationId, PropertyId, SourcePropertyDeclaration,
|
||||
parse_one_declaration_into, ComputedValues, Importance, LonghandId, PropertyDeclarationBlock,
|
||||
PropertyDeclarationId, PropertyId, SourcePropertyDeclaration,
|
||||
};
|
||||
use style::selector_parser::PseudoElement;
|
||||
use style::shared_lock::SharedRwLock;
|
||||
|
@ -80,7 +81,7 @@ pub struct LayoutThreadData {
|
|||
pub resolved_style_response: String,
|
||||
|
||||
/// A queued response for the resolved font style for canvas.
|
||||
pub parse_font_response: Option<ServoArc<ComputedValues>>,
|
||||
pub resolved_font_style_response: Option<ServoArc<Font>>,
|
||||
|
||||
/// A queued response for the offset parent/rect of a node.
|
||||
pub offset_parent_response: OffsetParentResponse,
|
||||
|
@ -179,10 +180,10 @@ impl LayoutRPC for LayoutRPCImpl {
|
|||
ResolvedStyleResponse(rw_data.resolved_style_response.clone())
|
||||
}
|
||||
|
||||
fn parsed_font(&self) -> Option<ServoArc<ComputedValues>> {
|
||||
fn resolved_font_style(&self) -> Option<ServoArc<Font>> {
|
||||
let &LayoutRPCImpl(ref rw_data) = self;
|
||||
let rw_data = rw_data.lock().unwrap();
|
||||
rw_data.parse_font_response.clone()
|
||||
rw_data.resolved_font_style_response.clone()
|
||||
}
|
||||
|
||||
fn offset_parent(&self) -> OffsetParentResponse {
|
||||
|
@ -800,14 +801,14 @@ where
|
|||
)
|
||||
}
|
||||
|
||||
pub fn process_parse_font_request<'dom, E>(
|
||||
pub fn process_resolved_font_style_request<'dom, E>(
|
||||
context: &LayoutContext,
|
||||
node: E,
|
||||
value: &str,
|
||||
property: &PropertyId,
|
||||
url_data: ServoUrl,
|
||||
shared_lock: &SharedRwLock,
|
||||
) -> Option<ServoArc<ComputedValues>>
|
||||
) -> Option<ServoArc<Font>>
|
||||
where
|
||||
E: LayoutNode<'dom>,
|
||||
{
|
||||
|
@ -846,12 +847,14 @@ where
|
|||
};
|
||||
|
||||
// 3. Resolve the parsed value with resolved styles of the parent element
|
||||
Some(resolve_for_declarations::<E>(
|
||||
let computed_values = resolve_for_declarations::<E>(
|
||||
&context.style_context,
|
||||
Some(&*parent_style),
|
||||
declarations,
|
||||
shared_lock,
|
||||
))
|
||||
);
|
||||
|
||||
Some(computed_values.clone_font())
|
||||
}
|
||||
|
||||
/// Return the resolved value of property for a given (pseudo)element.
|
||||
|
|
|
@ -28,7 +28,8 @@ use style::computed_values::position::T as Position;
|
|||
use style::context::{StyleContext, ThreadLocalStyleContext};
|
||||
use style::dom::OpaqueNode;
|
||||
use style::dom::TElement;
|
||||
use style::properties::{ComputedValues, LonghandId, PropertyDeclarationId, PropertyId};
|
||||
use style::properties::style_structs::Font;
|
||||
use style::properties::{LonghandId, PropertyDeclarationId, PropertyId};
|
||||
use style::selector_parser::PseudoElement;
|
||||
use style::stylist::RuleInclusion;
|
||||
use style::traversal::resolve_style;
|
||||
|
@ -66,6 +67,9 @@ pub struct LayoutThreadData {
|
|||
/// A queued response for the resolved style property of an element.
|
||||
pub resolved_style_response: String,
|
||||
|
||||
/// A queued response for the resolved font style for canvas.
|
||||
pub resolved_font_style_response: Option<ServoArc<Font>>,
|
||||
|
||||
/// A queued response for the offset parent/rect of a node.
|
||||
pub offset_parent_response: OffsetParentResponse,
|
||||
|
||||
|
@ -140,8 +144,10 @@ impl LayoutRPC for LayoutRPCImpl {
|
|||
ResolvedStyleResponse(rw_data.resolved_style_response.clone())
|
||||
}
|
||||
|
||||
fn parsed_font(&self) -> Option<ServoArc<ComputedValues>> {
|
||||
unimplemented!()
|
||||
fn resolved_font_style(&self) -> Option<ServoArc<Font>> {
|
||||
let &LayoutRPCImpl(ref rw_data) = self;
|
||||
let rw_data = rw_data.lock().unwrap();
|
||||
rw_data.resolved_font_style_response.clone()
|
||||
}
|
||||
|
||||
fn offset_parent(&self) -> OffsetParentResponse {
|
||||
|
|
|
@ -52,8 +52,9 @@ use layout::parallel;
|
|||
use layout::query::{
|
||||
process_client_rect_query, process_content_box_request, process_content_boxes_request,
|
||||
process_element_inner_text_query, process_node_scroll_area_request,
|
||||
process_node_scroll_id_request, process_offset_parent_query, process_parse_font_request,
|
||||
process_resolved_style_request, LayoutRPCImpl, LayoutThreadData,
|
||||
process_node_scroll_id_request, process_offset_parent_query,
|
||||
process_resolved_font_style_request, process_resolved_style_request, LayoutRPCImpl,
|
||||
LayoutThreadData,
|
||||
};
|
||||
use layout::sequential;
|
||||
use layout::traversal::{
|
||||
|
@ -558,7 +559,7 @@ impl LayoutThread {
|
|||
scroll_id_response: None,
|
||||
scroll_area_response: Rect::zero(),
|
||||
resolved_style_response: String::new(),
|
||||
parse_font_response: None,
|
||||
resolved_font_style_response: None,
|
||||
offset_parent_response: OffsetParentResponse::empty(),
|
||||
scroll_offsets: HashMap::new(),
|
||||
text_index_response: TextIndexResponse(None),
|
||||
|
@ -1232,8 +1233,8 @@ impl LayoutThread {
|
|||
&QueryMsg::ElementInnerTextQuery(_) => {
|
||||
rw_data.element_inner_text_response = String::new();
|
||||
},
|
||||
&QueryMsg::ParseFontQuery(..) => {
|
||||
rw_data.parse_font_response = None;
|
||||
&QueryMsg::ResolvedFontStyleQuery(..) => {
|
||||
rw_data.resolved_font_style_response = None;
|
||||
},
|
||||
&QueryMsg::InnerWindowDimensionsQuery(_) => {
|
||||
rw_data.inner_window_dimensions_response = None;
|
||||
|
@ -1555,10 +1556,10 @@ impl LayoutThread {
|
|||
rw_data.resolved_style_response =
|
||||
process_resolved_style_request(context, node, pseudo, property, root_flow);
|
||||
},
|
||||
&QueryMsg::ParseFontQuery(node, ref property, ref value) => {
|
||||
&QueryMsg::ResolvedFontStyleQuery(node, ref property, ref value) => {
|
||||
let node = unsafe { ServoLayoutNode::new(&node) };
|
||||
let url = self.url.clone();
|
||||
rw_data.parse_font_response = process_parse_font_request(
|
||||
rw_data.resolved_font_style_response = process_resolved_font_style_request(
|
||||
context,
|
||||
node,
|
||||
value,
|
||||
|
|
|
@ -914,7 +914,9 @@ impl LayoutThread {
|
|||
&QueryMsg::ResolvedStyleQuery(_, _, _) => {
|
||||
rw_data.resolved_style_response = String::new();
|
||||
},
|
||||
&QueryMsg::ParseFontQuery(_, _, _) => unimplemented!(),
|
||||
&QueryMsg::ResolvedFontStyleQuery(_, _, _) => {
|
||||
rw_data.resolved_font_style_response = None;
|
||||
},
|
||||
&QueryMsg::OffsetParentQuery(_) => {
|
||||
rw_data.offset_parent_response = OffsetParentResponse::empty();
|
||||
},
|
||||
|
@ -1207,7 +1209,7 @@ impl LayoutThread {
|
|||
fragment_tree,
|
||||
);
|
||||
},
|
||||
&QueryMsg::ParseFontQuery(_, _, _) => unimplemented!(),
|
||||
&QueryMsg::ResolvedFontStyleQuery(_, _, _) => unimplemented!(),
|
||||
&QueryMsg::OffsetParentQuery(node) => {
|
||||
rw_data.offset_parent_response = process_offset_parent_query(node);
|
||||
},
|
||||
|
|
|
@ -49,6 +49,7 @@ use std::cell::Cell;
|
|||
use std::fmt;
|
||||
use std::str::FromStr;
|
||||
use std::sync::Arc;
|
||||
use style::properties::style_structs::Font;
|
||||
|
||||
#[unrooted_must_root_lint::must_root]
|
||||
#[derive(Clone, JSTraceable, MallocSizeOf)]
|
||||
|
@ -86,6 +87,7 @@ pub(crate) struct CanvasContextState {
|
|||
shadow_offset_y: f64,
|
||||
shadow_blur: f64,
|
||||
shadow_color: RGBA,
|
||||
font_style: Option<Font>,
|
||||
}
|
||||
|
||||
impl CanvasContextState {
|
||||
|
@ -106,6 +108,7 @@ impl CanvasContextState {
|
|||
shadow_offset_y: 0.0,
|
||||
shadow_blur: 0.0,
|
||||
shadow_color: RGBA::transparent(),
|
||||
font_style: None,
|
||||
}
|
||||
}
|
||||
}
|
||||
|
@ -987,9 +990,18 @@ impl CanvasState {
|
|||
}
|
||||
|
||||
// https://html.spec.whatwg.org/multipage/#dom-context-2d-filltext
|
||||
pub fn fill_text(&self, text: DOMString, x: f64, y: f64, max_width: Option<f64>) {
|
||||
let is_max_width_finite = max_width.map_or(true, |max_width| max_width.is_finite());
|
||||
if !(x.is_finite() && y.is_finite() && is_max_width_finite) {
|
||||
pub fn fill_text(
|
||||
&self,
|
||||
_canvas: Option<&HTMLCanvasElement>,
|
||||
text: DOMString,
|
||||
x: f64,
|
||||
y: f64,
|
||||
max_width: Option<f64>,
|
||||
) {
|
||||
if !x.is_finite() || !y.is_finite() {
|
||||
return;
|
||||
}
|
||||
if max_width.map_or(false, |max_width| !max_width.is_finite() || max_width <= 0.) {
|
||||
return;
|
||||
}
|
||||
|
||||
|
@ -1008,14 +1020,17 @@ impl CanvasState {
|
|||
|
||||
// https://html.spec.whatwg.org/multipage/#dom-context-2d-font
|
||||
pub fn set_font(&self, canvas: Option<&HTMLCanvasElement>, value: DOMString) {
|
||||
let _resolved_font = if let Some(element) = canvas {
|
||||
let node = element.upcast::<Node>();
|
||||
let window = window_from_node(&*node);
|
||||
window.parse_font_query(&node, value.to_string())
|
||||
} else {
|
||||
None
|
||||
let canvas = match canvas {
|
||||
Some(element) => element,
|
||||
None => return,
|
||||
};
|
||||
unimplemented!()
|
||||
let node = canvas.upcast::<Node>();
|
||||
let window = window_from_node(&*canvas);
|
||||
let font_style = match window.resolved_font_style_query(&node, value.to_string()) {
|
||||
Some(value) => value,
|
||||
None => return, // syntax error
|
||||
};
|
||||
self.state.borrow_mut().font_style = Some((*font_style).clone());
|
||||
}
|
||||
|
||||
// https://html.spec.whatwg.org/multipage/#dom-context-2d-font
|
||||
|
|
|
@ -144,6 +144,7 @@ use style::context::QuirksMode;
|
|||
use style::dom::OpaqueNode;
|
||||
use style::element_state::*;
|
||||
use style::media_queries::MediaList;
|
||||
use style::properties::style_structs::Font;
|
||||
use style::properties::PropertyDeclarationBlock;
|
||||
use style::selector_parser::{PseudoElement, Snapshot};
|
||||
use style::shared_lock::{Locked as StyleLocked, SharedRwLock as StyleSharedRwLock};
|
||||
|
@ -479,6 +480,7 @@ unsafe_no_jsmanaged_fields!(NetworkError);
|
|||
unsafe_no_jsmanaged_fields!(Atom, Prefix, LocalName, Namespace, QualName);
|
||||
unsafe_no_jsmanaged_fields!(TrustedPromise);
|
||||
unsafe_no_jsmanaged_fields!(PropertyDeclarationBlock);
|
||||
unsafe_no_jsmanaged_fields!(Font);
|
||||
// These three are interdependent, if you plan to put jsmanaged data
|
||||
// in one of these make sure it is propagated properly to containing structs
|
||||
unsafe_no_jsmanaged_fields!(DocumentActivity, WindowSizeData, WindowSizeType);
|
||||
|
|
|
@ -288,7 +288,8 @@ impl CanvasRenderingContext2DMethods for CanvasRenderingContext2D {
|
|||
|
||||
// https://html.spec.whatwg.org/multipage/#dom-context-2d-filltext
|
||||
fn FillText(&self, text: DOMString, x: f64, y: f64, max_width: Option<f64>) {
|
||||
self.canvas_state.fill_text(text, x, y, max_width);
|
||||
self.canvas_state
|
||||
.fill_text(self.canvas.as_ref().map(|c| &**c), text, x, y, max_width);
|
||||
self.mark_as_dirty();
|
||||
}
|
||||
|
||||
|
|
|
@ -60,11 +60,6 @@ impl OffscreenCanvasRenderingContext2D {
|
|||
));
|
||||
reflect_dom_object(boxed, global)
|
||||
}
|
||||
/*
|
||||
pub fn get_canvas_state(&self) -> Ref<CanvasState> {
|
||||
self.canvas_state.borrow()
|
||||
}
|
||||
*/
|
||||
|
||||
pub fn set_canvas_bitmap_dimensions(&self, size: Size2D<u64>) {
|
||||
self.canvas_state.set_bitmap_dimensions(size);
|
||||
|
@ -249,7 +244,13 @@ impl OffscreenCanvasRenderingContext2DMethods for OffscreenCanvasRenderingContex
|
|||
|
||||
// https://html.spec.whatwg.org/multipage/#dom-context-2d-filltext
|
||||
fn FillText(&self, text: DOMString, x: f64, y: f64, max_width: Option<f64>) {
|
||||
self.canvas_state.fill_text(text, x, y, max_width)
|
||||
self.canvas_state.fill_text(
|
||||
self.htmlcanvas.as_ref().map(|c| &**c),
|
||||
text,
|
||||
x,
|
||||
y,
|
||||
max_width,
|
||||
)
|
||||
}
|
||||
|
||||
// https://html.spec.whatwg.org/multipage/#textmetrics
|
||||
|
|
|
@ -137,7 +137,8 @@ use style::dom::OpaqueNode;
|
|||
use style::error_reporting::{ContextualParseError, ParseErrorReporter};
|
||||
use style::media_queries;
|
||||
use style::parser::ParserContext as CssParserContext;
|
||||
use style::properties::{ComputedValues, PropertyId, ShorthandId};
|
||||
use style::properties::style_structs::Font;
|
||||
use style::properties::{PropertyId, ShorthandId};
|
||||
use style::selector_parser::PseudoElement;
|
||||
use style::str::HTML_SPACE_CHARACTERS;
|
||||
use style::stylesheets::CssRuleType;
|
||||
|
@ -1848,16 +1849,16 @@ impl Window {
|
|||
)
|
||||
}
|
||||
|
||||
pub fn parse_font_query(&self, node: &Node, value: String) -> Option<ServoArc<ComputedValues>> {
|
||||
pub fn resolved_font_style_query(&self, node: &Node, value: String) -> Option<ServoArc<Font>> {
|
||||
let id = PropertyId::Shorthand(ShorthandId::Font);
|
||||
if !self.layout_reflow(QueryMsg::ParseFontQuery(
|
||||
if !self.layout_reflow(QueryMsg::ResolvedFontStyleQuery(
|
||||
node.to_trusted_node_address(),
|
||||
id,
|
||||
value,
|
||||
)) {
|
||||
return None;
|
||||
}
|
||||
self.layout_rpc.parsed_font()
|
||||
self.layout_rpc.resolved_font_style()
|
||||
}
|
||||
|
||||
pub fn layout(&self) -> &dyn LayoutRPC {
|
||||
|
@ -2513,11 +2514,11 @@ fn debug_reflow_events(id: PipelineId, reflow_goal: &ReflowGoal, reason: &Reflow
|
|||
&QueryMsg::NodeScrollGeometryQuery(_n) => "\tNodeScrollGeometryQuery",
|
||||
&QueryMsg::NodeScrollIdQuery(_n) => "\tNodeScrollIdQuery",
|
||||
&QueryMsg::ResolvedStyleQuery(_, _, _) => "\tResolvedStyleQuery",
|
||||
&QueryMsg::ResolvedFontStyleQuery(..) => "\nResolvedFontStyleQuery",
|
||||
&QueryMsg::OffsetParentQuery(_n) => "\tOffsetParentQuery",
|
||||
&QueryMsg::StyleQuery => "\tStyleQuery",
|
||||
&QueryMsg::TextIndexQuery(..) => "\tTextIndexQuery",
|
||||
&QueryMsg::ElementInnerTextQuery(_) => "\tElementInnerTextQuery",
|
||||
&QueryMsg::ParseFontQuery(..) => "\nParseFontQuery",
|
||||
&QueryMsg::InnerWindowDimensionsQuery(_) => "\tInnerWindowDimensionsQuery",
|
||||
},
|
||||
};
|
||||
|
|
|
@ -117,7 +117,7 @@ pub enum QueryMsg {
|
|||
ResolvedStyleQuery(TrustedNodeAddress, Option<PseudoElement>, PropertyId),
|
||||
StyleQuery,
|
||||
ElementInnerTextQuery(TrustedNodeAddress),
|
||||
ParseFontQuery(TrustedNodeAddress, PropertyId, String),
|
||||
ResolvedFontStyleQuery(TrustedNodeAddress, PropertyId, String),
|
||||
InnerWindowDimensionsQuery(BrowsingContextId),
|
||||
}
|
||||
|
||||
|
@ -146,7 +146,7 @@ impl ReflowGoal {
|
|||
QueryMsg::NodeScrollGeometryQuery(_) |
|
||||
QueryMsg::NodeScrollIdQuery(_) |
|
||||
QueryMsg::ResolvedStyleQuery(..) |
|
||||
QueryMsg::ParseFontQuery(..) |
|
||||
QueryMsg::ResolvedFontStyleQuery(..) |
|
||||
QueryMsg::OffsetParentQuery(_) |
|
||||
QueryMsg::StyleQuery => false,
|
||||
},
|
||||
|
@ -168,7 +168,7 @@ impl ReflowGoal {
|
|||
QueryMsg::NodeScrollGeometryQuery(_) |
|
||||
QueryMsg::NodeScrollIdQuery(_) |
|
||||
QueryMsg::ResolvedStyleQuery(..) |
|
||||
QueryMsg::ParseFontQuery(..) |
|
||||
QueryMsg::ResolvedFontStyleQuery(..) |
|
||||
QueryMsg::OffsetParentQuery(_) |
|
||||
QueryMsg::InnerWindowDimensionsQuery(_) |
|
||||
QueryMsg::StyleQuery => false,
|
||||
|
|
|
@ -7,7 +7,7 @@ use euclid::default::Rect;
|
|||
use euclid::Size2D;
|
||||
use script_traits::UntrustedNodeAddress;
|
||||
use servo_arc::Arc;
|
||||
use style::properties::ComputedValues;
|
||||
use style::properties::style_structs::Font;
|
||||
use style_traits::CSSPixel;
|
||||
use webrender_api::ExternalScrollId;
|
||||
|
||||
|
@ -32,8 +32,8 @@ pub trait LayoutRPC {
|
|||
fn node_scroll_id(&self) -> NodeScrollIdResponse;
|
||||
/// Query layout for the resolved value of a given CSS property
|
||||
fn resolved_style(&self) -> ResolvedStyleResponse;
|
||||
/// Query layout to get the parsed font property for canvas.
|
||||
fn parsed_font(&self) -> Option<Arc<ComputedValues>>;
|
||||
/// Query layout to get the resolved font style for canvas.
|
||||
fn resolved_font_style(&self) -> Option<Arc<Font>>;
|
||||
fn offset_parent(&self) -> OffsetParentResponse;
|
||||
fn text_index(&self) -> TextIndexResponse;
|
||||
/// Requests the list of nodes from the given point.
|
||||
|
|
Loading…
Add table
Add a link
Reference in a new issue