parent
0bf0f58fa4
commit
2b69ff778f
|
@ -24,6 +24,7 @@ use std::mem;
|
|||
pub struct Gradient {
|
||||
pub geometry: GradientGeometry,
|
||||
stops: Vec<ColorStop>,
|
||||
pub wrap: GradientWrap,
|
||||
}
|
||||
|
||||
#[derive(Clone, Copy, PartialEq, Debug)]
|
||||
|
@ -49,6 +50,12 @@ pub enum GradientGeometry {
|
|||
}
|
||||
}
|
||||
|
||||
#[derive(Clone, Copy, PartialEq, Debug)]
|
||||
pub enum GradientWrap {
|
||||
Clamp,
|
||||
Repeat,
|
||||
}
|
||||
|
||||
impl Eq for Gradient {}
|
||||
|
||||
impl Hash for Gradient {
|
||||
|
@ -90,7 +97,11 @@ impl Hash for ColorStop {
|
|||
impl Gradient {
|
||||
#[inline]
|
||||
pub fn linear(line: LineSegment2F) -> Gradient {
|
||||
Gradient { geometry: GradientGeometry::Linear(line), stops: Vec::new() }
|
||||
Gradient {
|
||||
geometry: GradientGeometry::Linear(line),
|
||||
stops: Vec::new(),
|
||||
wrap: GradientWrap::Clamp,
|
||||
}
|
||||
}
|
||||
|
||||
#[inline]
|
||||
|
@ -104,6 +115,7 @@ impl Gradient {
|
|||
Gradient {
|
||||
geometry: GradientGeometry::Radial { line: line.to_line(), radii, transform },
|
||||
stops: Vec::new(),
|
||||
wrap: GradientWrap::Clamp,
|
||||
}
|
||||
}
|
||||
|
||||
|
|
|
@ -9,13 +9,13 @@
|
|||
// except according to those terms.
|
||||
|
||||
use crate::allocator::{AllocationMode, TextureAllocator};
|
||||
use crate::gpu_data::{ColorCombineMode, RenderCommand, TextureLocation, TextureMetadataEntry, TexturePageDescriptor};
|
||||
use crate::gpu_data::{TexturePageId, TileBatchTexture};
|
||||
use crate::gpu_data::{ColorCombineMode, RenderCommand, TextureLocation, TextureMetadataEntry};
|
||||
use crate::gpu_data::{TexturePageDescriptor, TexturePageId, TileBatchTexture};
|
||||
use crate::scene::{RenderTarget, SceneId};
|
||||
use hashbrown::HashMap;
|
||||
use pathfinder_color::ColorU;
|
||||
use pathfinder_content::effects::{BlendMode, Filter, PatternFilter};
|
||||
use pathfinder_content::gradient::{Gradient, GradientGeometry};
|
||||
use pathfinder_content::gradient::{Gradient, GradientGeometry, GradientWrap};
|
||||
use pathfinder_content::pattern::{Pattern, PatternSource};
|
||||
use pathfinder_content::render_target::RenderTargetId;
|
||||
use pathfinder_geometry::line_segment::LineSegment2F;
|
||||
|
@ -368,12 +368,20 @@ impl Palette {
|
|||
let color_texture_metadata = paint.overlay.as_ref().map(|overlay| {
|
||||
match overlay.contents {
|
||||
PaintContents::Gradient(ref gradient) => {
|
||||
let mut sampling_flags = TextureSamplingFlags::empty();
|
||||
match gradient.wrap {
|
||||
GradientWrap::Repeat => {
|
||||
sampling_flags.insert(TextureSamplingFlags::REPEAT_U);
|
||||
}
|
||||
GradientWrap::Clamp => {}
|
||||
}
|
||||
|
||||
// FIXME(pcwalton): The gradient size might not be big enough. Detect this.
|
||||
let location = gradient_tile_builder.allocate(allocator, gradient);
|
||||
PaintColorTextureMetadata {
|
||||
location,
|
||||
page_scale: allocator.page_scale(location.page),
|
||||
sampling_flags: TextureSamplingFlags::empty(),
|
||||
sampling_flags,
|
||||
filter: match gradient.geometry {
|
||||
GradientGeometry::Linear(_) => PaintFilter::None,
|
||||
GradientGeometry::Radial { line, radii, .. } => {
|
||||
|
|
|
@ -17,7 +17,7 @@ use hashbrown::HashMap;
|
|||
use pathfinder_color::ColorU;
|
||||
use pathfinder_content::dash::OutlineDash;
|
||||
use pathfinder_content::fill::FillRule;
|
||||
use pathfinder_content::gradient::{ColorStop, Gradient};
|
||||
use pathfinder_content::gradient::{ColorStop, Gradient, GradientWrap};
|
||||
use pathfinder_content::outline::Outline;
|
||||
use pathfinder_content::segment::{Segment, SegmentFlags};
|
||||
use pathfinder_content::stroke::{LineCap, LineJoin, OutlineStrokeToFill, StrokeStyle};
|
||||
|
@ -56,7 +56,6 @@ bitflags! {
|
|||
const UNSUPPORTED_LINK_PAINT = 0x0020;
|
||||
const UNSUPPORTED_FILTER_ATTR = 0x0040;
|
||||
const UNSUPPORTED_MASK_ATTR = 0x0080;
|
||||
const UNSUPPORTED_GRADIENT_SPREAD_METHOD = 0x0100;
|
||||
}
|
||||
}
|
||||
|
||||
|
@ -237,11 +236,27 @@ impl SVGScene {
|
|||
id: String,
|
||||
usvg_base_gradient: &BaseGradient) {
|
||||
for stop in &usvg_base_gradient.stops {
|
||||
gradient.add(ColorStop::from_usvg_stop(stop));
|
||||
let mut stop = ColorStop::from_usvg_stop(stop);
|
||||
if usvg_base_gradient.spread_method == SpreadMethod::Reflect {
|
||||
stop.offset *= 0.5;
|
||||
}
|
||||
gradient.add(stop);
|
||||
}
|
||||
|
||||
if usvg_base_gradient.spread_method != SpreadMethod::Pad {
|
||||
self.result_flags.insert(BuildResultFlags::UNSUPPORTED_GRADIENT_SPREAD_METHOD);
|
||||
// Reflect gradient if necessary.
|
||||
if usvg_base_gradient.spread_method == SpreadMethod::Reflect {
|
||||
for stop in &usvg_base_gradient.stops {
|
||||
let mut stop = ColorStop::from_usvg_stop(stop);
|
||||
if usvg_base_gradient.spread_method == SpreadMethod::Reflect {
|
||||
stop.offset = 1.0 - stop.offset * 0.5;
|
||||
}
|
||||
gradient.add(stop);
|
||||
}
|
||||
}
|
||||
|
||||
match usvg_base_gradient.spread_method {
|
||||
SpreadMethod::Pad => {}
|
||||
SpreadMethod::Reflect | SpreadMethod::Repeat => gradient.wrap = GradientWrap::Repeat,
|
||||
}
|
||||
|
||||
let transform = usvg_transform_to_transform_2d(&usvg_base_gradient.transform);
|
||||
|
@ -304,7 +319,6 @@ impl Display for BuildResultFlags {
|
|||
"non-color paint",
|
||||
"filter attribute",
|
||||
"mask attribute",
|
||||
"gradient spread method",
|
||||
];
|
||||
}
|
||||
}
|
||||
|
|
Loading…
Reference in New Issue