When the member limit is reached among the paths of a compound clipping
path that has geometry effects of its own, the compound path still
becomes one path of its reshaped geometry. The paths that were not
visited go into that geometry as they are, and their own effects are
not applied. The doc comment of with_clip_effects_applied_while said
that they keep their effects, which holds for the members of a group or
layer only.
New test a_compound_clipping_path_takes_its_own_effect_at_the_member_limit
covers the compound path.
A group or layer in a clipping path that has geometry effects of its
own is walked once for its members' effects and once for its own, and
its members count toward the member limit each time. The doc comment
of members_as_drawn now states this.
When a group's geometry effects evaluate the members of the group, a
clip group's clipping path takes the geometry effects in it first. A
clipping path that is a group, layer or compound path had each of its
members reshaped at every depth without counting them, so a large
clipping path was reshaped past the SYMBOL_ART_MAX_NODES members that
members_as_drawn documents.
Each member of a clipping path now counts as one visited member. Once
the limit is reached, that member and the members after it keep their
effects, as the other members past the limit do. The canvas, the
export bake and clipping type are unchanged: they do not count members.
A path's Drop Shadow, glow, blur, Feather or pixel filter listed before a
Transform effect that makes copies was drawn once under all the copies, at
the object's own distances. Each copy now carries those raster effects,
scaled by the copy's mean scale, with a Drop Shadow's offset turned,
reflected and scaled with the copy. Raster effects listed after the
Transform effect still paint once around all the copies. Copies that stop
at the effect budget keep their effects, and a Transform effect without
copies draws as before.
The canvas, the object's bounds, export, baking and Expand Appearance use
the same art. Type, images, symbol instances, groups, a fill's or stroke's
own copying Transform effect, and paths with Rasterize or an SVG filter
before the copying effect keep one set of raster effects.
Evaluating a layer's Pathfinder or geometry effects asked each member
whether a sublayer below it held a ruler guide, then asked the members
of every selected sublayer or group the same question again on the way
down. A sublayer nested N deep was scanned once per layer or group above
it, so a chain of N sublayers cost N(N+1)/2 scans.
One read walk now looks at each member once at most and records which
members hold or lead to a sublayer's guides, and the move visits and
copies only those. As before, the groups inside a sublayer that holds no
guide are not looked into. The guides taken, their order, their hidden
and locked state, the art left behind and the sharing of untouched
members are the same as before.
Type used as a clip group's clipping path, with a geometry effect on the
object, on one of its fills or strokes, or a perspective, was baked into
its outlined pieces with the effects applied, so SVG, PDF and the other
exports clipped by all of them while the canvas clips by the plain glyph
outlines. The baked clipping path was also a group, so the type's fills
and strokes were not painted.
bake_node now bakes such a clip group as the canvas draws it: the
clipping path is a path of the region effects::clip_outline gives, the
type's fills (effects baked) paint behind the clipped art inside the
clip, and its strokes paint over it outside the clip, in a group that
keeps the clip group's id and transparency.
Create Outlines copied each character run's fills and strokes onto every
glyph, ruby glyph and underline or strikethrough bar as they were, so a
gradient with no vector of its own refitted to each piece's own box,
while the canvas fits it across the whole layout. A gradient with a
vector kept its text-space coordinates in the document, and the
characters' stroke kept its text-space weight on scaled type.
Each piece is now painted by paint_type_piece, the rule outline_text
already used: unplaced gradients are fixed to the layout's bounds, then
the type's transform places the piece, its gradients, stroke weights and
pattern tiles. Object > Expand outlines type the same way, and
object.expand.info measures gradient fills on the same paths.
Three cases still clipped differently from what the clipping path draws:
- A clip group with an appearance of its own (a Drop Shadow, a geometry
effect) was measured for culling by its plain clipping path, so a view
showing only the part of the clip that an effect moved drew nothing.
The renderer now grows that measure by the clip region in this case
too.
- The geometry effects on the fills and strokes of an unpainted clipping
path applied after the effects of a group around it. They now apply
first, as for other members. A clipping path that paints keeps them
live, so its fill and stroke still draw.
- Export baked a compound clipping path with an effect of its own from
its raw paths, dropping the effects on those paths. It now bakes the
clipping path as the canvas clips by it, and the pieces it bakes into
get ids of their own.
An instance whose baked art passed the export's placed symbol art budget,
or drew too deep, gave its count back, so any number of instances could
each bake their art in full and be dropped without the work counting.
- Art baked and then dropped is now counted with the placed art against
the budget, both before more art is baked and when baked art is checked.
- While an instance's art bakes, the art's objects before baking are held
in the budget, so instances nested in it are placed only within what is
left.
Documents whose placed art fits the budget export as before.
Checking an Extrude & Bevel (both kinds) or Inflate effect built every
shape's profile about the profiles' bounds, then built the fill and
stroke solids again about the bounds of the regions they paint. A
filled shape's profile is its fill's solid, so that solid was built
twice. When a stroke reaches past the shape, the first build also used
bounds the effect does not draw it about.
The check now builds the profile on its own only where no drawn solid
is built from it: every shape for Rotate, and for Extrude & Bevel and
Inflate a shape with no fill (strokes only, or no paint). A filled
shape's solid is built once, about the bounds the effect draws it
about. The shadow check is unchanged.
Tests count the solids the check builds: an object with a fill and a
stroke, a group of two such members, an effect on the fill and the
shadow on; a shape with no fill still has its profile built.
An instance whose symbol art has live effects is replaced in the export by a group holding the baked art. That group now takes the instance's attributes as well, so a PDF export keeps the instance's URL as a link annotation over the art where its effects draw it.
Hidden instances, instances in hidden groups, on template layers, and
on hidden layers or layers that do not print when the exporter leaves
those out are no longer placed for PDF, print, EPS and DXF. Their art
was baked and counted toward the 16,000,000-object limit for placed
symbol art, so it could leave a visible instance written without its
effects.
bake_document_placing_symbols takes a WrittenLayers value: PDF passes
the layers its settings write, EPS writes layers that do not print but
not hidden ones, and DXF writes both. Print removes the layers that do
not print before baking.
When PDF, print, EPS and DXF export place a symbol's art to bake its
effects, the art now carries the stain the instance's fill gives it, as
it did before the art was placed. The art is stained first and its
effects apply to the stained colors.
A Fill + Offset Path below a group's Contents painted every clipped member
of a clip group among its members, so art hidden outside the clipping path
bulged the offset outline. A clip group (or clipping layer) now adds the
region its clipping path clips to.
PDF, print, EPS and DXF exports now check the art of each placed symbol
instance after its effects are baked. The objects it holds, including
the copies a Transform effect makes, opacity mask art and the art of
instances placed inside it (counted once), count against the export's
16,000,000-object budget. An instance whose baked art passes the budget,
or would draw deeper than the 128 levels a document may draw, stays an
instance.
- doc: DrawnHeights measures how deep an object outside the layers
draws, symbols and patterns it uses included.
- effects: the bake tracks how deep each baked object sits, and a
rejected candidate releases what it and the instances in it charged.
Revolve sorted its faces by the depth of each face's middle only, so a
tilted profile with long edges, or a profile of several contours, could
draw a nearer face under a farther one where the two overlap.
- A revolved face carries its view-space plane (none when its corners lie
off one plane or reach the eye), and Revolve (Classic)'s facets keep it.
- Revolve and Revolve (Classic) put each surface's faces through the local
depth order Extrude & Bevel uses for its fill and strokes: when two
overlapping faces are drawn the wrong way round, every pair of
overlapping faces goes in the order of their depths at the middle of the
overlap, within the same 4,000,000-comparison limit. A surface already
in the right order keeps it.
- A group's members, sorted together by depth, go through the same order
across members.
Docs: docs/revolve.md, docs/effects-parity.md, docs/target-app-parity.md.
PDF, print, EPS and DXF wrote a symbol instance by placing its symbol's
art as stored, so live effects inside that art were missing: a square
moved 100 pt by a Transform effect stayed in place in the file while the
canvas drew it moved.
bake_document_placing_symbols replaces each instance of a symbol whose
art (or the art of a symbol nested in it) needs baking by that art
placed as the instance places it, then baked. The art is placed before
its effects apply, as on the canvas, so an instance that scales its art
does not scale what its effects do. A dynamic instance's own paint
changes apply before baking. Nesting stops at 32 levels and the placed
art at 16,000,000 objects per export; past them an instance stays an
instance. DXF places 9-slice cells unclipped, as its scene does. The
symbols' own art, SVG and the .ai editing data are unchanged, and HPGL
already baked each placed instance.
A raster effect (Drop Shadow, Outer Glow, Gaussian Blur and the other
effects that paint pixels) on a symbol instance's topmost fill now draws
on each filled shape of the symbol's art, and one on its topmost stroke
draws on each stroked shape, after any geometry effects listed before
it. The same rules as for geometry effects apply: only a visible fill or
stroke with an opacity above 0 counts, a group's own fills and strokes
in the art take the effect, and an instance inside the art passes it on.
The canvas, Use Preview Bounds and the drawn bounds, SVG and PDF export
draw it, and Object > Expand Appearance is enabled for such an instance:
a shadow or glow becomes an image under the instance, and a blur,
feather or inner glow replaces it with the image, in one undo step.
Existing documents with a raster effect on a symbol instance's fill or
stroke draw differently: before, the effect drew nothing.
A clipping path with Roughen, Transform or another effect that reshapes
a path drew its own fill and stroke reshaped, but the canvas and raster
export still clipped the art by the plain path. SVG and PDF export bake
the effect into the path before writing the clip path, so the screen
and a saved SVG showed different art.
effects::clip_outline now applies the live geometry effects in the
clipping path before taking its region: the path's or compound path's
own effects, the effects of its fills and strokes (the region is then
the union of the paths they give, as an export bakes them), the effects
of a compound path's paths, of a group's visible members and of a
nested clip group's clipping path, shown or hidden, and a group's own
effects as an export evaluates them. Raster effects such as Gaussian
Blur leave the region as it is. The renderer, the engine commands that
measure a clip region (flatten, arrowheads, cutting) and the writers use
it; the writers receive the baked document, so their output for a path
with effects does not change.
The renderer measures a clip group by the region its clipping path's
effects give it, so a view or tile that shows only the moved part of
the clip still draws the clipped art, and it drops cached clip regions
that hold a plug-in effect when plug-ins change.
Two rules change in every export as well as on the canvas:
- When the clip group, or a group around it, has a geometry effect of
its own, the clipping path's effects apply first and its gradients
move with them. #7114 left the clipping path's effects live under the
group's effect, so they applied after it.
- Type used as a clipping path keeps its own effects when a group's
effect outlines it. #2073 and #2290 outlined it without them, to
match the plain clip the canvas drew.
Expand as Wireframes reshaped the faces of a 3D effect with the geometry
effects after it, but the faces it built carried no stroke. An Outline
Stroke after the 3D effect then outlined a plain 1 pt stroke with miter
joins, while the canvas outlines the round-joined stroke each face is
drawn with: the seam stroke (half the facet's thickness, 0.05 to 0.75 pt;
0.75 pt on Revolve) or the 0.5 pt wire edge of the Classic Wireframe
surface. The wireframe's faces now carry that stroke, so the expanded
edges lie where the drawn outlines lie.
A geometry effect after an object's 3D effect, such as a Transform that
scales or rotates about the center, measures the drawn art, cast shadow
included. Expand as Wireframes measured the faces alone, so with a
shadow on, the expanded edges landed away from the surfaces on the
canvas. The faces are now reshaped together with the shadow the canvas
draws behind them (Extrude & Bevel, Inflate, Rotate and Revolve, on an
object, group or layer), and only the faces are kept.