Revert #200 (text always continuously rasterised): breaks kinetic_typography
The QA test's time-remapped precomp no longer matches the precomp rendered directly (crates/automation/tests/qa/kinetic.rs:78); FreeBSD CI has been red since. Reverting until the PR is reworked against that test. Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
This commit is contained in:
parent
d5f78f3fc0
commit
29c4d3ad15
|
|
@ -667,21 +667,18 @@ impl<'a> Renderer<'a> {
|
||||||
Region::Full
|
Region::Full
|
||||||
}
|
}
|
||||||
|
|
||||||
/// Rasterisation scale of a layer's source: the output scale, or — for text layers, which are
|
/// Rasterisation scale of a layer's source: the output scale, or — for Continuously
|
||||||
/// always continuously rasterised, and Continuously Rasterize shape layers and vector footage —
|
/// Rasterize text and shape layers — the output scale times the layer's on-screen scale
|
||||||
/// the output scale times the layer's on-screen scale (quarter-octave steps, rounded up, so
|
/// (quarter-octave steps, rounded up, so vector content is drawn at its final size and
|
||||||
/// vector content is drawn at its final size and stays sharp when scaled up).
|
/// stays sharp when scaled up).
|
||||||
pub fn raster_scale(&self, ctx: &EvalCtx, layer: &Layer) -> f64 {
|
pub fn raster_scale(&self, ctx: &EvalCtx, layer: &Layer) -> f64 {
|
||||||
let s = self.opts.scale;
|
let s = self.opts.scale;
|
||||||
let continuous = match layer.source {
|
let vector = match layer.source {
|
||||||
LayerSource::Text => true,
|
LayerSource::Text | LayerSource::Shape => true,
|
||||||
LayerSource::Shape => layer.switches.collapse,
|
LayerSource::Footage { item } => matches!(self.project.item(item).map(|i| &i.kind), Some(ItemKind::Footage(f)) if is_vector_footage(f)),
|
||||||
LayerSource::Footage { item } => {
|
|
||||||
layer.switches.collapse && matches!(self.project.item(item).map(|i| &i.kind), Some(ItemKind::Footage(f)) if is_vector_footage(f))
|
|
||||||
}
|
|
||||||
_ => false,
|
_ => false,
|
||||||
};
|
};
|
||||||
if !continuous {
|
if !layer.switches.collapse || !vector {
|
||||||
return s;
|
return s;
|
||||||
}
|
}
|
||||||
let (l2c, _) = ctx.layer_to_comp(layer);
|
let (l2c, _) = ctx.layer_to_comp(layer);
|
||||||
|
|
|
||||||
|
|
@ -1,7 +1,7 @@
|
||||||
//! Collapse Transformations, Continuously Rasterize and the Quality switch.
|
//! Collapse Transformations, Continuously Rasterize and the Quality switch.
|
||||||
|
|
||||||
use effectcraft_color::{BlendMode, Label};
|
use effectcraft_color::{BlendMode, Label};
|
||||||
use effectcraft_keyframe::{TextDoc, Value};
|
use effectcraft_keyframe::Value;
|
||||||
use effectcraft_project::build::{self, Ids};
|
use effectcraft_project::build::{self, Ids};
|
||||||
use effectcraft_project::{BitDepth, Comp, ItemId, ItemKind, Layer, LayerSource, Project, Quality, Solid};
|
use effectcraft_project::{BitDepth, Comp, ItemId, ItemKind, Layer, LayerSource, Project, Quality, Solid};
|
||||||
use effectcraft_time::{FrameRate, Tick};
|
use effectcraft_time::{FrameRate, Tick};
|
||||||
|
|
@ -234,32 +234,3 @@ fn collapsed_precomp_of_another_size_renders_through_the_parent_camera() {
|
||||||
assert!(img.get(100, 100)[3] < 0.01, "only the 40 px solid is drawn");
|
assert!(img.get(100, 100)[3] < 0.01, "only the 40 px solid is drawn");
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
/// Text layers are always continuously rasterised (#194): text scaled up with the layer's Scale is drawn
|
|
||||||
/// at its on-screen size, as sharp as text set at that font size, without the switch.
|
|
||||||
#[test]
|
|
||||||
fn text_scaled_up_stays_sharp_without_the_switch() {
|
|
||||||
let run = |size: f64, scale: f64| {
|
|
||||||
let mut p = project();
|
|
||||||
let comp = Comp::new(240, 160, FrameRate::FPS_30, Tick::from_seconds_f64(2.0));
|
|
||||||
let mut l = build::layer(&mut p, &comp, "Text", LayerSource::Text, (240, 160), None);
|
|
||||||
l.props.prop_mut("text/sourceText").unwrap().value = Value::Text(Box::new(TextDoc { text: "HE".into(), size, ..Default::default() }));
|
|
||||||
set(&mut l, "transform/anchor", Value::Vec3([0.0, 0.0, 0.0]));
|
|
||||||
set(&mut l, "transform/position", Value::Vec3([40.0, 120.0, 0.0]));
|
|
||||||
set(&mut l, "transform/scale", Value::Vec3([scale, scale, 100.0]));
|
|
||||||
assert!(!l.switches.collapse);
|
|
||||||
let mut c = comp;
|
|
||||||
c.layers = vec![l];
|
|
||||||
let cid = p.add_item("Comp", Label::Sandstone, None, ItemKind::Comp(c.into()));
|
|
||||||
render_frame(&p, cid, Tick::ZERO, 1.0)
|
|
||||||
};
|
|
||||||
let partial = |img: &Image| img.data.iter().filter(|px| (0.02..0.98).contains(&px[3])).count();
|
|
||||||
let scaled = run(10.0, 800.0);
|
|
||||||
let native = run(80.0, 100.0);
|
|
||||||
let (ps, pn) = (partial(&scaled), partial(&native));
|
|
||||||
let d = max_diff(&scaled, &native);
|
|
||||||
eprintln!("partially covered pixels: scaled {ps}, native {pn}; max difference {d}");
|
|
||||||
assert!(native.data.iter().filter(|px| px[3] > 0.98).count() > 1000, "the text renders");
|
|
||||||
assert!(ps <= pn + pn / 2, "scaled text is blurred: {ps} soft pixels against {pn}");
|
|
||||||
assert!(d < 0.05, "scaled text differs from text set at that size by {d}");
|
|
||||||
}
|
|
||||||
|
|
|
||||||
|
|
@ -318,9 +318,8 @@ hierarchical block-matching optical flow and a bidirectional warp (Pixel Motion,
|
||||||
its nested layers straight into the parent with concatenated transforms (one resample), so
|
its nested layers straight into the parent with concatenated transforms (one resample), so
|
||||||
nested blend modes and adjustment layers act on the parent's layers; nested 3D layers use the
|
nested blend modes and adjustment layers act on the parent's layers; nested 3D layers use the
|
||||||
parent's camera and lights and, when the precomp layer is 3D, are depth-sorted with the parent's
|
parent's camera and lights and, when the precomp layer is 3D, are depth-sorted with the parent's
|
||||||
3D run. Masks, effects or styles force a flattened render. Text layers are always rasterised at
|
3D run. Masks, effects or styles force a flattened render. On text and shape layers the switch is
|
||||||
their on-screen scale; on shape layers and vector footage the switch is Continuously Rasterize and
|
Continuously Rasterize: the source is rasterised at its on-screen scale. Quality: Draft samples
|
||||||
does the same. Quality: Draft samples
|
|
||||||
nearest-neighbour, Wireframe draws the layer bounds. Slip edit (`layer.slip`, Alt+PageUp/Down,
|
nearest-neighbour, Wireframe draws the layer bounds. Slip edit (`layer.slip`, Alt+PageUp/Down,
|
||||||
dragging the source bar in the timeline) moves the source under fixed in/out points.
|
dragging the source bar in the timeline) moves the source under fixed in/out points.
|
||||||
|
|
||||||
|
|
|
||||||
Loading…
Reference in New Issue