返回 ppt-master
native-shape-authoring.md
根目录 / skills / ppt-master / references / native-shape-authoring.md
1 > See [`shared-standards-core.md`](./shared-standards-core.md) §§1.4–1.5 for the native-shape metadata and validation contracts.
2
3 # Native Shape Authoring Reference
4
5 Use this reference during Executor SVG construction or project-owned canonical
6 template maintenance when native contours or supported shape/text operands can
7 express the intended object. Choose each contour from its page job before
8 deciding how to encode it, then use the simplest exact authoring form. Keep
9 faithful atoms independent unless one contour is required; materialize that
10 contour with a PowerPoint-style Boolean result, and use hand-authored freeform
11 only when those constructions fail. Neither helper writes a page. The preset
12 helper does not create the shape's own `p:txBody`; keep visible text outside the
13 atomic fragment.
14
15 **Mandatory — complete vocabulary before contour selection**: In Create
16 Template, load this reference and
17 [`preset-shape-vocabulary.md`](./preset-shape-vocabulary.md) completely and
18 retain both as soon as `replication_mode` resolves to `standard` or `fidelity`,
19 before selecting any newly authored page or template contour. Do not load this
20 authored-construction bundle for `mirror`; it preserves source-owned geometry.
21 In every other valid authoring context, read the preset vocabulary completely
22 at authoring entry before selecting the first newly authored contour. It exposes
23 all 187 exact preset names under the Office gallery and objective contour
24 families. This is authoring-side capability knowledge, never a Strategist task
25 or Design Spec field. Reread only after context invalidation or a known file
26 change; a filtered query cannot replace the complete read.
27
28 **Hard rule — direct structured calls**: `${SKILL_DIR}` below is the retained
29 absolute Skill root. After choosing a concrete lookup or authoring operation,
30 invoke that command once per argument set and read stdout directly. Do not
31 change CWD, encode executables or flag lists in scalar shell strings, batch
32 these calls through shell loops, merge stderr, or add a downstream parser when
33 `--compact` exists.
34
35 `list --search` and `list --grouped --search` are optional spelling/location
36 helpers. Run `describe <name> --compact` only when a serious candidate needs
37 objective identity, adjustment, connector, path, connection-site, or
38 text-rectangle facts. Executor makes the final comparison through §§1–2.1;
39 filtered lookup cannot narrow the already-loaded vocabulary.
40
41 ## 1. Contour Selection and Materialization Gate
42
43 **Hard rule — contour before encoding**: choose the page-fit contour from the
44 intended job and active visual system across the full native vocabulary before
45 considering authoring syntax. Rectangle, rounded-rectangle, circle, and ellipse
46 contours are not an earlier visual tier merely because SVG has short primitive
47 syntax for them. Easier syntax is never the reason to select a contour.
48
49 **Default — exact page-fit geometry before generic neutrality (may override when
50 neutrality itself communicates the page)**: Resolve relationship fit when the
51 content carries direction, sequence, membership, hierarchy, convergence, reveal,
52 or contrast. Independently resolve page-field / carrier fit from ownership,
53 focal hierarchy, boundary strength, and the active deck's edge / opening
54 language; `Structure=no` removes only relationship topology. Choose a plain
55 primitive, uniform grid, or no drawn carrier only when that lack of inflection
56 gives the reader a concrete benefit or avoids a false inference. Retain that
57 reader effect through authoring. Before that neutral result wins, name the
58 strongest fitting native / compound alternative and retain why its inflection
59 would add no reader benefit, create a false inference, weaken hierarchy, or
60 conflict with the page job. Quick speed, restrained style, readability, equal
61 importance, precedent, and shorter syntax alone do not qualify.
62
63 **Hard rule — style does not narrow capability**: the active visual system may
64 weight contour fit and control paint, stroke, texture, density, and recurrence.
65 It never removes primitives, Office presets, independent composition, Boolean,
66 or necessary freeform from consideration. Style-specific syntax guidance
67 applies only to the named style-defining mark, not every functional page
68 contour.
69
70 After contour selection, use the simplest exact materialization below. Do not
71 hand-author a freeform merely because an SVG path is convenient.
72
73 | Selected result | Authoring form |
74 |---|---|
75 | Mirror/preserve input already owns native-shape metadata | Keep the existing object and metadata; never reselect its preset. |
76 | One exact non-Connector stock contour | Use an ordinary SVG primitive only when the exporter maps it to that same contour; otherwise run `preset_shape_svg.py render` and insert its complete stdout fragment. |
77 | A stock `bentConnector*` / `curvedConnector*` contour exactly expresses a bent or curved relationship and endpoint attachment is not required | Run `preset_shape_svg.py render --object-kind connector`; the result is an unconnected native Connector shape. |
78 | A straight relationship, divider, or leader | Write `<line>`; use a registered marker under [`shared-standards-core.md`](./shared-standards-core.md) §1.1 only when direction is meaningful. |
79 | A selected text/content boundary needs no filled surface | Use its exact authoring form with `fill="none"` and a visible stroke; keep its content as independent siblings. |
80 | Two or more selected native contours form the page construction but do not need one contour | Keep them as independently editable siblings in one ordinary semantic group; use §2.1 to compose the page-level geometry system. |
81 | Two or more supported closed-shape / resolvable-text operands require Union, Combine, Fragment, Intersect, or Subtract | Run `shape_boolean_svg.py render`, then replace the operands with every stdout path; the result remains ordinary editable custom geometry. |
82 | Exact native contours, their independent composition, and Boolean materialization cannot faithfully express the visual meaning or contour | Write ordinary `<path>` / `<polygon>` geometry; export keeps it as editable custom geometry. |
83 | The shape only resembles a preset | Never infer a preset; continue to the Boolean gate, then use freeform only if no faithful construction exists. |
84
85 **Hard rule**: `preset_shape_svg.py` is the only authoring entry for
86 `data-pptx-authoring="preset"`. Never add `data-pptx-prst`, frame, adjustment,
87 or registry path data by hand. Insert the helper's complete compact `<g>` and
88 rerun the helper whenever its geometry, paint, or filter reference changes.
89 After selecting two or more objects for one current page or template
90 construction, use `render-batch --input -` to validate and emit their
91 independent fragments in one stdout round; the batch never chooses those
92 objects or their composition.
93
94 ---
95
96 ## 2. Vocabulary-Guided Preset Selection
97
98 [`preset-shape-vocabulary.md`](./preset-shape-vocabulary.md) follows the Office
99 gallery taxonomy: Lines, Rectangles, Basic Shapes, Block Arrows, Equation
100 Shapes, Flowchart, Stars and Banners, Callouts, and Action Buttons. Its family
101 labels and objective identities expose the available contours without deciding
102 their page use. The optional semantic helper data does not redefine the
103 DrawingML registry or override Executor judgment.
104
105 Apply this page-local sequence before drawing:
106
107 | Pass | Action | Result |
108 |---|---|---|
109 | Job | State what the object must do for the reader before naming a shape. | Page role plus any real relationship, direction, aspect, text load, or literal scope. |
110 | Browse | Compare that job against the complete loaded vocabulary; move from Office category to contour family to exact name. | A small candidate set chosen by meaning, not syntax convenience. |
111 | Inspect | When exact facts could change the decision, run `describe --compact` directly for those candidates and compare identity, scope, adjustments, connector status, paths, text rectangle, and connection sites. | Objective geometry evidence without prescribed use. |
112 | Select | Choose the contour whose inference and visual character fit the page, including a neutral primitive when neutrality is useful. | One page-fit contour; no syntax decision yet. |
113 | Encode | Apply §1's materialization gate. | Ordinary SVG primitive, helper-authored preset, Boolean result, or necessary freeform. |
114
115 Example location and inspection commands:
116
117 ```bash
118 python3 "${SKILL_DIR}/scripts/preset_shape_svg.py" describe chevron --compact
119 python3 "${SKILL_DIR}/scripts/preset_shape_svg.py" list --search connector
120 ```
121
122 **Hard rule — semantic fit, not name association**: a preset name, topic word,
123 or metaphor is not evidence of use. Respect `literal_only` and `scope` before
124 visual preference. For example, a scroll is not a generic playbook carrier, a
125 lightning bolt is not generic price tension, `chartX` / `chartStar` /
126 `chartPlus` are partition symbols rather than charts, and a flowchart symbol
127 belongs only in an actual flowchart. An action-button preset supplies visual
128 geometry only; it never creates an action or hyperlink.
129
130 The vocabulary exposes contours; Executor chooses them, and §1 chooses syntax.
131 It never requires `rect`, `ellipse`, `line`, or any other primitive to pass
132 through the preset helper. Export never scans or upgrades existing geometry.
133
134 **Shape-first diagram rule**: use `<line>` for straight thin relationships;
135 use an exact connector-family preset for a stock bent or curved contour; use a
136 block-arrow / chevron preset for a solid direction. Resort to an open freeform
137 path only when those native constructions cannot faithfully express the
138 relationship, data geometry, or locked hand-drawn / organic style. Newly
139 authored connector-family presets remain unconnected and do not gain attachment
140 semantics. Existing Connector topology imported from a source PPTX remains
141 owned by the preserve/mirror round-trip contract.
142
143 **Forbidden — false native semantics**:
144
145 - a catalog entry with `literal_only=true` when the depicted literal concept is
146 absent, or a `flowchart` / `navigation` scope outside that real context;
147 - `actionButton*` when navigation or trigger behavior is expected; the helper
148 maps its visual preset geometry only and never creates an action or hyperlink;
149 - `chartX`, `chartStar`, or `chartPlus` as a substitute for native charts;
150 - logo, icon glyph, illustration, brand contour, or data-chart marks.
151
152 ### 2.1 Compound page geometry
153
154 **Trigger**: after the page or prototype's communication / slot job, composition
155 anchors, and any applicable topology under
156 [`executor-structure.md`](./executor-structure.md) are resolved, but before
157 writing coordinates, resolve the page-scale geometry move that best carries its
158 background field, content zoning, focal hierarchy, or reading path. Apply §1's
159 exact-fit decision and compare the useful lenses below. Before repeating stacked
160 rectangles / rounded cards or uniform equal columns, compare a page-field,
161 outline, nesting, or continuity construction and the relevant contour family's
162 exact members. Readability of the first workable arrangement does not close this
163 gate.
164 This applies whether the per-page Structure result is `no` or `yes`; it never
165 creates a decoration requirement.
166
167 | Pass | Action | Result |
168 |---|---|---|
169 | Page job | Name the page-scale geometry move and its jobs: surface, boundary, focal mark, shared region, counterweight, or any source-backed direction / reveal. | One composition direction and a small set of functional zones; no shape names yet. |
170 | Decompose | Separate visible content from geometric atoms. Identify which atoms need independent movement, paint, or reuse and which contour must become one object. | Editable siblings plus any explicit Boolean operand set. |
171 | Select | Choose the contour family, then its exact member from the job, full native vocabulary, and edge / corner / opening behavior; retain the reader effect when the result is generic or undrawn. | Page-fit native atoms without syntax bias. |
172 | Compose | Establish page frame, scale, z-order, and negative space with independent atoms. Keep text, images, icons, data marks, and non-merged accents outside Boolean operands. | One page-level geometry system, not a collection of unrelated decorations. |
173 | Materialize | Run the preset helper for each adopted preset. Run the Boolean helper only for contours that require Merge Shapes semantics, then replace those operands with its stdout paths. | Valid authoring SVG ready for native export. |
174
175 **Composition lenses — not a checklist**:
176
177 | Lens | Use when it strengthens the resolved page |
178 |---|---|
179 | Page field | Let one large surface, outline, aperture, or off-canvas contour organize major zones instead of wrapping every content unit in a card. |
180 | Outline carrier | Use `fill="none"` plus a coherent stroke on a frame, arc, bracket, band, or other faithful contour when bare text needs ownership without a heavy filled card. |
181 | Nested fields | Visually nest an inset contour, secondary surface, badge, port, or focal shape inside / across a larger field to create hierarchy; keep them as siblings unless one contour must merge. |
182 | Continuity | Align or overlap independent shapes across zones so geometry reinforces the intended reading path. |
183 | Depth and contrast | Combine filled, outlined, offset, and negative-space atoms; use Boolean only when the contour itself must change. |
184 | Deck language | Reuse a corner, arc, slant, notch, or layering logic with page-fit variation rather than cloning one composition. |
185
186 **Default — running deck geometry check (may override for literal pages or
187 isolated template prototypes)**: After each generated page, retain
188 `page job → composition move → contour / edge language`; append `relationship →
189 topology` only for `Structure=yes`, then compare before the next. Repeat only for
190 the same page job / relationship or deliberate continuity; section, equal
191 weight/density, style, and precedent are insufficient. Create no artifact or
192 second pass.
193
194 **Boolean decision gate**:
195
196 | Required result | Construction |
197 |---|---|
198 | Stock contour already expresses the job | Keep that exact contour and materialize it through §1; do not rebuild it from other shapes or Boolean operands. |
199 | Shapes overlap or layer but must remain independently editable | Keep separate primitives / presets in one ordinary semantic group; do not merge them. |
200 | One continuous outer silhouette | `union`; use `combine` only for intentional symmetric negative regions. |
201 | A true hole, edge cut, or reveal | `subtract`, with the visible body first and cutout operands after it. |
202 | Only the common covered region should remain | `intersect`. |
203 | Exclusive and shared regions need separate styling or motion | `fragment`, retaining every required result path as an independent shape. |
204
205 **Authoring-to-export map**:
206
207 | SVG authoring form | Native PPTX result |
208 |---|---|
209 | Ordinary `<rect>`, rounded `<rect>`, `<circle>`, `<ellipse>`, or `<line>` | Matching editable preset geometry / line shape. |
210 | Complete `preset_shape_svg.py` fragment | One exact `a:prstGeom` shape, or `p:cxnSp` for an authored connector preset. |
211 | `shape_boolean_svg.py` result path | Editable `a:custGeom`; the final contour is retained, not replayable Merge Shapes history. |
212 | Parent semantic group containing independent atoms and content | A grouped page construction whose child shapes remain separately editable. |
213
214 **Reference — not a constraint**: derive the operand count, preset choices,
215 geometry, paint, rotation, and grouping from the current page. A strong compound
216 construction may use only independent presets, only one Boolean result, or a mix;
217 there is no Boolean quota and no catalog of allowed combinations.
218
219 **Hard rule — merge only geometry that must become one contour**: never merge
220 text, images, icons, or otherwise independent accents merely to simplify the
221 SVG tree. Boolean materialization discards editable operand history; preserve
222 siblings whenever one-object contour semantics are unnecessary.
223
224 ---
225
226 ## 3. Fragment Generation
227
228 `render` emits one selected object. `render-batch` atomically emits multiple
229 already-selected objects for one current page or template construction.
230 Generated project pages choose each object's solid paint from the current page
231 context, using `spec_lock.md` roles as reusable anchors rather than an exhaustive
232 palette; `create-template` takes colors from the confirmed brief and template
233 `design_spec.md`. Mirror/preserve input keeps the source object's paint instead
234 of regenerating this authored form.
235
236 ```bash
237 python3 ${SKILL_DIR}/scripts/preset_shape_svg.py render rightArrow \
238 --id p03-growth-arrow \
239 --frame 160 210 320 112 \
240 --fill "#2563EB" \
241 --stroke none \
242 --adjust "adj1=val 50000"
243 ```
244
245 When one native effect is justified, append `--filter-id softShadow`.
246 `softShadow` must already be one direct page-level `<defs><filter>` id under
247 [`svg-effects.md`](./svg-effects.md) §6.4. Omit the option otherwise.
248
249 For a stock bent / curved contour that does not require endpoint attachment:
250
251 ```bash
252 python3 ${SKILL_DIR}/scripts/preset_shape_svg.py render bentConnector3 \
253 --id p03-flow-connector \
254 --object-kind connector \
255 --frame 420 180 220 140 \
256 --fill none \
257 --stroke "#475569" \
258 --stroke-width 2
259 ```
260
261 Every connector-family preset requires `--object-kind connector`, `--fill none`,
262 and a visible stroke. It exports as an unconnected `p:cxnSp`; a connector
263 preset can never be authored as an ordinary `shape`.
264
265 **Hard rule — stdout-only exception**: the helper prints one or more
266 deterministic `<g>` fragments. Read that output and insert it with the normal
267 page/template `apply_patch` edit. A batch JSON array is transient input for
268 already-selected objects in the current construction, never a project resource
269 or multi-page plan. Do not redirect output into `svg_output/`, loop over
270 pages/templates, or let the helper choose layout. The main Agent still authors
271 each complete SVG page and reusable template explicitly.
272
273 ---
274
275 ## 4. Atomic Fragment Contract
276
277 The helper emits one compact logical group. Metadata and base paint are written
278 once on the group; its direct children are the visible paths regenerated from
279 the locked preset registry.
280
281 | Component | Ownership |
282 |---|---|
283 | Logical `<g data-pptx-authoring="preset">` | Stable id, object kind, preset, frame, adjustments, explicit local base paint, and an optional helper-authored shape filter reference. |
284 | Direct `<path>` children | Ordered browser-visible registry layers. A child writes only a path-specific fill/stroke override when the preset requires one. |
285 | Deliberately absent transport fields | No hidden carrier, preview wrapper, `data-pptx-part`, or stored fingerprint belongs in project-authored SVG. Those fields remain part of expanded PPTX import/round-trip transport. |
286
287 **Hard rule**: treat the returned group as atomic. Keep it as the content group
288 without `data-pptx-bounds` when it stands alone; `data-pptx-frame` owns its
289 object geometry. When it needs labels, icons, or other decorations, put the
290 preset and those siblings in a separate bounded parent content group; never put
291 them inside the preset group itself. Do not edit the direct paths; they are
292 validation evidence generated from the registry, not a freehand contour surface.
293
294 Canonical page/template authoring also keeps paint and opacity off ancestor
295 groups that contain the preset. Compatible ancestor paint still exports under
296 the general SVG composition rules, but the checker warns because the atom is no
297 longer paint-self-contained; rerun the helper with channel alpha instead.
298
299 On a structured template, a validated authored-preset group is one semantic
300 atom. It may be Slide-local, the single carrier of an `object` slot, or a direct
301 Master/Layout fixed atom. This narrow exception does not permit ordinary nested
302 `<g>` structures in Master/Layout layers or placeholder carriers. The template
303 workflow may add the registered structural ownership attributes to the complete
304 helper group; it still must not alter preset metadata, paint, the filter
305 reference, or direct paths.
306
307 **Frame coordinate space**: `--frame x y w h` is expressed in the coordinate
308 space where you insert the fragment. At the page root that is page coordinates;
309 inside a `<g transform="translate(…)">` use **group-local** coordinates — the
310 ancestor transform stacks on top, so page-absolute values would double-offset
311 the shape off-canvas. Keep the helper's exact space-separated ordinary-decimal
312 `data-pptx-frame` spelling; compact authoring does not accept alternate numeric
313 spellings.
314
315 **Regeneration rule**: rerun the helper when preset, frame, adjustment, fill,
316 stroke, stroke width, or the filter id changes. Moving, scaling, rotating, or
317 flipping the complete logical group is allowed; zero-scale transforms and
318 shear/skew are forbidden, and the transformed frame must remain inside
319 DrawingML's coordinate range. Stroke width must remain inside DrawingML's
320 line-width range. To freely edit the contour, replace the whole fragment with
321 ordinary SVG rather than modifying a generated direct path.
322
323 For a canonical reusable template, the complete helper fragment may remain as
324 an executable exemplar. A final-page adaptation may copy it unchanged only
325 when all registry metadata, frame, adjustments, paint, and the optional filter
326 reference remain unchanged; otherwise regenerate the complete compact group.
327
328 ---
329
330 ## 5. Boundaries
331
332 | Concern | Behavior |
333 |---|---|
334 | Shape text | Keep visible SVG `<text>` outside the atomic fragment. It remains editable but may export as a grouped text box rather than the preset's own `p:txBody`. |
335 | Connector attachment | Authoring helper v1 creates an unconnected `p:cxnSp` and does not accept endpoint/site metadata. Do not hand-add it. The imported-shape contract may preserve an attachment that already exists in a source PPTX; creating a new attached connector is currently unsupported. |
336 | Action button behavior | `actionButton*` presets map visual geometry only. No action, navigation target, or hyperlink is created automatically. |
337 | Gradient/pattern paint | Authoring helper v1 accepts solid HEX paint only. Use ordinary SVG when a complex paint treatment is essential. |
338 | Shadow/glow | Shape presets may reference one existing [`svg-effects.md`](./svg-effects.md) §6.4 filter through `--filter-id`; it applies once to the complete native shape. Connector presets, multiple effects, child-path filters, and other effect graphs remain unsupported. |
339 | Multi-path darken/lighten | Direct visible layers use the shared normalized paint behavior from the PPTX importer. Their registry-derived HEX values are authorized derivatives of the selected base color and need no separate lock row. |
340 | Expanded compatibility | Existing helper-authored carrier/preview fragments remain readable as ordinary Slide-local input and receive a non-blocking migration warning; they do not become structured fixed atoms or object-slot carriers. Imported expanded fragments remain the lossless mirror/preserve form. |
341 | External edits | Any registry-path, style, or semantic mismatch fails quality check and export; regenerate the fragment. |
342
343 **Validation**: `svg_quality_checker.py` independently rerenders every compact
344 authored preset from registry metadata and compares its direct visible paths
345 and paint. It also validates the optional shape filter through the shared
346 [`svg-effects.md`](./svg-effects.md) §6.4 contract. The exporter performs the
347 same validation, then expands the compact group only in memory to reuse the
348 lossless native-shape conversion path.
349 Compatible expanded authored input remains under its separate carrier/preview
350 freshness contract.
351
352 ---
353
354 ## 6. Shape Boolean Materialization
355
356 **Trigger**: Current page construction has two or more supported shape/text operands
357 whose faithful result calls for PowerPoint-style Union, Combine, Fragment,
358 Intersect, or Subtract. Executor decides this directly from the actual content,
359 complete native inventory, and explicit user/template constraints; no upstream
360 suggestion or planning field is required.
361
362 ```bash
363 python3 ${SKILL_DIR}/scripts/shape_boolean_svg.py render <svg-file> \
364 --operation subtract \
365 --source body \
366 --source cutout \
367 --id result
368 ```
369
370 | Concern | Contract |
371 |---|---|
372 | Sources | Closed `path`, `polygon`, `rect`, `circle`, `ellipse`, one validated unfiltered compact authored shape preset, or supported horizontal implicit-LTR direct `<text>` with a resolvable exact OpenType weight/style (`--font-dir` adds search roots). Text becomes glyph geometry and is no longer editable text. A filtered preset is not a Boolean operand; materialize the geometry without the effect, then reapply one supported filter to the result. Open geometry, groups, nested text, images, definitions, and nested SVG viewports fail closed. |
373 | Primary shape | The first `--source` supplies result paint. For `subtract`, all later operands are removed from that primary geometry. Explicit paint flags override only their named channels. |
374 | Coordinates | Ancestor and local transforms are baked into SVG-root coordinate space. Place stdout in the primary operand's z-order with no additional transform; never reinsert it under an original transformed ancestor. Root-coordinate space does not require each result path to be a direct `<svg>` child. |
375 | Placement | Ordinary Slide-local results belong in the applicable untransformed direct-root semantic `<g>` with its normal `id` / `data-pptx-bounds`. Master/Layout results remain direct-root path atoms and redeclare `data-pptx-layer`. One non-fragment result may be the direct `data-pptx-carrier="true"` child of an `object` slot. |
376 | Fragment roles | Fragment paths may share one ordinary Slide-local semantic group, but remain separate shapes and cannot collectively claim one carrier or one Master/Layout atom. Helper output inherits no structural role metadata from its operands; redeclare only the final layer/carrier/role contract. |
377 | Result | `union`, `combine`, `intersect`, and `subtract` emit one ordinary `<path>`. `fragment` emits stable sibling paths named `<id>-1`, `<id>-2`, ... in top/left/bottom/right/area order. |
378 | Winding | Results use explicit nonzero contour direction and never emit `fill-rule`, `clip-rule`, `clip-path`, `mask`, or Merge Shapes metadata. Operands that depend on even-odd fill, clipping, or masking fail closed. |
379 | Preservation | This helper authors new geometry only. Never use it to merge or split mirror/preserve source structure. |
380
381 Operation semantics match PowerPoint's visible Merge Shapes result: `union`
382 keeps every covered region, `combine` keeps the symmetric difference,
383 `intersect` keeps only common coverage, `subtract` removes every later source
384 from the primary, and `fragment` returns each atomic filled region. The PPTX
385 stores the materialized freeform geometry, not replayable operation history.
386
387 **Hard rule — stdout-only replacement**: The helper never writes the source
388 page. In one normal `apply_patch` edit, remove every selected operand and insert
389 every returned path in root coordinate space at the primary operand's z-order,
390 using the placement contract above. Fragment paths remain separate shapes; an
391 ordinary semantic group does not turn them into one structural atom.
392
393 ---
394
395 ## 7. Shape-Only Modelling Techniques
396
397 Applies to any page built from shapes, **with or without images** — a text-only,
398 data-only, or icon-only deck reaches these the same way. Each technique below is
399 plain geometry plus gradient paint, so all of it survives native export.
400
401 ### 7.1 Alternating light/dark gradient = dimensional form
402
403 The single highest-yield shape technique. A cylinder, metallic band, dimensional
404 numeral, or curved panel is produced by one gradient whose stops **alternate
405 light and dark** across the shape — light · dark · light for a three-stop ramp,
406 or light · dark · light · dark · light for a five-stop one. The alternation
407 imitates a curved surface catching light twice; a plain two-stop ramp always
408 reads flat no matter how strong the contrast.
409
410 Keep every stop on one hue and vary only lightness, hold one light direction for
411 the whole page, and remove strokes so adjacent facets meet cleanly. For a
412 cylinder, apply the alternating ramp across the body and cap it with an ellipse
413 carrying its own shallower ramp. The same light logic applies across separate
414 facets of any folded form.
415
416 ### 7.2 Reflection without a reflection effect
417
418 Native reflection is `Bake-required` ([`svg-effects.md`](./svg-effects.md) §6.12),
419 so build it from geometry instead:
420
421 1. Duplicate the object and flip it with `transform="translate(0, 2·y_bottom) scale(1, -1)"`.
422 2. Keep only the top **10–25 %** of the flipped copy — that is all a reflection
423 ever shows.
424 3. Lay a rectangle over it filled with a gradient running from fully transparent
425 at the object's base to the page background color at the cut line, so the
426 copy dissolves into the page.
427 4. Drop the whole reflection to roughly **60–70 %** opacity.
428
429 Seat rows of certificates, product shots, logo tiles, and cylinders this way. Do
430 not add a blur — it will not survive export, and a short gradient fade already
431 reads correctly at slide scale.
432
433 ### 7.3 Fragment as a modelling tool, not just a boolean
434
435 `fragment` (§6) is the fastest way to build layered diagrams from one silhouette:
436 lay evenly distributed bars across a triangle and fragment it into pyramid tiers;
437 cross a circle with two bars for a quadrant wheel; slice an annulus radially for
438 ring segments. Every piece inherits the parent contour, so the assembly stays
439 perfectly registered — impossible to achieve by drawing the tiers separately.
440
441 Distribute the cutting bars with a constant step before fragmenting; uneven tiers
442 read as a mistake rather than a hierarchy. Paint the resulting pieces with one
443 gradient family per §7.1 so the stack reads as a single solid.
444
445 ### 7.4 Soft edges without the soft-edge effect
446
447 Feathered edges are `Bake-required` ([`svg-effects.md`](./svg-effects.md) §6.12),
448 but the four jobs they normally do are all reachable with gradients:
449
450 | Intent | Build instead |
451 |---|---|
452 | Contact shadow under an object | Ellipse filled with a `radialGradient` from dark-transparent at the centre to fully transparent at the rim |
453 | Spotlight / stage pool | Cone or ellipse filled with a gradient fading to transparent at its far end, at low opacity over the scene |
454 | Object dissolving into the page | Overlay a rectangle whose gradient runs from transparent to the exact page background hex |
455 | Hiding an object while keeping it live | Full transparency, or a background-registered fill ([`image-layout-patterns.md`](./image-layout-patterns.md) `#M1-08`) |
456
457 A radial or linear alpha ramp reads the same as a feathered edge at slide scale
458 and, unlike a filter, exports intact. Never approximate a soft edge with a stack
459 of stroked outlines — the banding is visible on projection.
460
461 ### 7.5 Ground plane and staging
462
463 An object floating in empty canvas looks pasted on. Give it a surface: a wide
464 shallow ellipse or trapezoid beneath it, filled with a gradient that fades to the
465 background at its edges, optionally with a soft dark ellipse directly under the
466 object as contact shadow. A trapezoid narrowing away from the viewer reads as a
467 receding floor; a cylinder or slab reads as a pedestal.
468
469 Keep the plane low-contrast — it is staging, not content. This is what makes
470 certificate rows, product hero shots, and trophy/award pages look composed
471 rather than floating, and it costs two shapes.
472
472 lines MARKDOWN