mirror of
https://github.com/storytold/vectorcraft.git
synced 2026-10-30 20:58:00 -06:00
M3.59: tints of global and spot colours, tint swatches and Global colour balance
A colour linked to a global or spot swatch keeps a tint (Paint::Solid.tint, 1 by default and
left out of files at 100 %): paint.setFill/setStroke {swatch, tint} apply the swatch at that
percentage, swatch edits recolour every linked colour at its own tint, and Color::tinted
resolves it (CMYK and Gray inks scale, RGB mixes toward white). swatch.new saves a tint as a
tint swatch ("Ink 40%") linked to its base. Spot tints separate as that percentage of their
plate (Separations Preview, PDF Separation value) instead of an ink-ratio guess. Adjust Color
Balance's Global mode (tint) shifts the tints of linked colours. The Color panel shows Tint
mode (the swatch chip, its name and a T slider) for linked colours; the Swatches panel
highlights the tint swatch in use. Gradient stops get the same link and tint fields (the
swatch walks cover them), so GradientStop is no longer Copy.
Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
This commit is contained in:
co-authored by
Claude Opus 5.5
parent
e94748dc17
commit
b2ececc7b4
+16
-12
@@ -2,6 +2,7 @@
|
||||
|
||||
use std::collections::HashMap;
|
||||
|
||||
use krilla::color::separation::{Color as SepColor, SeparationColorant, SeparationSpace};
|
||||
use krilla::color::{cmyk, luma, rgb};
|
||||
use krilla::configure::{Archival, ConfigurationBuilder, PdfVersion};
|
||||
use krilla::geom::{Path, PathBuilder, Size, Transform};
|
||||
@@ -242,19 +243,22 @@ impl Exporter<'_> {
|
||||
color(c)
|
||||
}
|
||||
|
||||
/// A solid paint, as a Separation colour space when it's linked to a spot swatch (the
|
||||
/// swatch's CMYK equivalent is the alternate space).
|
||||
fn solid(&mut self, c: &Color, swatch: Option<&str>) -> krilla::color::Color {
|
||||
use krilla::color::separation::{Color as SepColor, SeparationColorant, SeparationSpace};
|
||||
let spot = swatch.and_then(|n| self.doc.swatch(n).filter(|s| s.spot)).and_then(|s| s.paint.color().map(|sc| (s.name.clone(), sc)));
|
||||
let Some((name, sc)) = spot else { return self.col(c) };
|
||||
/// The Separation colour space of spot swatch `name` (its CMYK equivalent is the alternate
|
||||
/// space); `None` when `name` isn't a spot colour.
|
||||
fn separation(&self, name: &str) -> Option<SeparationSpace> {
|
||||
let sw = self.doc.swatch(name).filter(|s| s.spot)?;
|
||||
let cms = vectorcraft_color::cms::active();
|
||||
let intent = cms.settings().intent;
|
||||
let full = cms.to_cmyk(&sc, intent);
|
||||
let total: f32 = full.iter().sum();
|
||||
let tint = if total <= 1e-4 { 1.0 } else { (cms.to_cmyk(c, intent).iter().sum::<f32>() / total).clamp(0.0, 1.0) };
|
||||
let full = cms.to_cmyk(&sw.paint.color()?, cms.settings().intent);
|
||||
let alt = krilla::color::RegularColor::Cmyk(cmyk::Color::new(q(full[0]), q(full[1]), q(full[2]), q(full[3])));
|
||||
SepColor::new(q(tint), SeparationSpace::new(SeparationColorant::Custom(name), alt)).into()
|
||||
Some(SeparationSpace::new(SeparationColorant::Custom(sw.name.clone()), alt))
|
||||
}
|
||||
|
||||
/// A solid paint, in the Separation colour space at its tint when it's linked to a spot swatch.
|
||||
fn solid(&mut self, c: &Color, link: Option<&str>, tint: f32) -> krilla::color::Color {
|
||||
match link.and_then(|n| self.separation(n)) {
|
||||
Some(space) => SepColor::new(q(tint), space).into(),
|
||||
None => self.col(c),
|
||||
}
|
||||
}
|
||||
|
||||
/// Warn when `effects` (an object's, a fill's or a stroke's) has a visible raster effect.
|
||||
@@ -275,7 +279,7 @@ impl Exporter<'_> {
|
||||
fn paint(&mut self, p: &Paint, bounds: Rect) -> Option<krilla::paint::Paint> {
|
||||
match p {
|
||||
Paint::None => None,
|
||||
Paint::Solid { color: c, swatch } => Some(self.solid(c, swatch.as_deref()).into()),
|
||||
Paint::Solid { color: c, swatch, tint } => Some(self.solid(c, swatch.as_deref(), *tint).into()),
|
||||
Paint::Gradient(g) => {
|
||||
let geom = g.resolve(bounds);
|
||||
let mut stops: Vec<Stop> = Vec::new();
|
||||
|
||||
@@ -397,7 +397,7 @@ fn shading_gradient(sp: &hayro_interpret::pattern::ShadingPattern) -> Option<Gra
|
||||
keep.push(N);
|
||||
let stop_at = |t: f32, offset: f32| -> GradientStop {
|
||||
let (color, _) = sample(t).unwrap_or((Color::BLACK, 1.0));
|
||||
GradientStop { offset, color, opacity: 1.0, midpoint: 0.5 }
|
||||
GradientStop::new(offset, color)
|
||||
};
|
||||
let c = |x: f32, y: f32| m * Point::new(x as f64, y as f64);
|
||||
let (kind, geom, stops) = if *axial {
|
||||
|
||||
Reference in New Issue
Block a user