feat: tree transform#526
Draft
RobertFrenken wants to merge 5 commits into
Draft
Conversation
Adds d3-hierarchy layout transforms following Observable Plot's *Node/*Link paired convention: - treeNode/treeLink: tree and cluster diagrams - treemapNode: space-filling rectangular treemaps - packNode: circle-packing layouts - partitionNode/partitionLink: icicle/sunburst partition layouts Shared infrastructure in hierarchy.ts provides stratification (flat data → hierarchy) and a WeakMap cache that deduplicates layout computation across paired transforms. Includes docs page, sidebar entries, 5 tree examples, flare.csv dataset, and 59 tests across 4 test files. Co-Authored-By: Claude Opus 4.6 (1M context) <noreply@anthropic.com>
- Fix record interface types: [key: string]: unknown → any, add [key: symbol]: any for compatibility with Record<string|symbol, RawValue> - Move examples from examples/graph/ to per-transform directories (examples/tree/, treemap/, pack/, partition/) to fix prerender 404 caused by [group] route resolving graph → /marks/graph - Wrap computed values in $derived() for Svelte 5 reactivity correctness - Add `as [number, number]` tuple casts on size options - Apply Prettier formatting to all new files Co-Authored-By: Claude Opus 4.6 (1M context) <noreply@anthropic.com>
✅ Deploy Preview for svelteplot ready!
To edit notification comments on pull requests, go to your Netlify project configuration. |
Co-Authored-By: Claude Opus 4.6 (1M context) <noreply@anthropic.com>
- Wire delimiter option through buildHierarchy() — d3's stratify().path() hardcodes '/' as separator, so custom delimiters (like '.') are now converted before passing to d3. This was the root cause of flat/broken hierarchy plots. - Fix Text marks rendering literal "null" — filter data to leaf nodes before passing to <Text> instead of returning null from the accessor (String(null) → "null" in Text.svelte). - Normalize padding as fraction of layout size in treemap/pack/partition — padding: 0.01 now means 1% regardless of layout size parameter. - Fix treemap/partition examples: padding was in absolute layout units, consuming entire space with size: [1,1]. Pack example: switched to normalized coordinates with derived pixelSize for r conversion. - Expose two-tier API: treeLayout, treemapLayout, packLayout, partitionLayout as public low-level functions returning raw d3 hierarchy roots. Matches the force transform's forceLayout / forceNode pattern. Co-Authored-By: Claude Opus 4.6 (1M context) <noreply@anthropic.com>
- Generate screenshot thumbnails for all hierarchy examples (tree, treemap, pack, partition) via screenshot-examples.js on OSC. - Add --no-sandbox and --disable-setuid-sandbox to Puppeteer launch options, required for headless Chrome on HPC compute nodes and CI. Co-Authored-By: Claude Opus 4.6 (1M context) <noreply@anthropic.com>
This was referenced Mar 23, 2026
Contributor
|
I set this back to draft as it needs some more work. |
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment
Add this suggestion to a batch that can be applied as a single commit.This suggestion is invalid because no changes were made to the code.Suggestions cannot be applied while the pull request is closed.Suggestions cannot be applied while viewing a subset of changes.Only one suggestion per line can be applied in a batch.Add this suggestion to a batch that can be applied as a single commit.Applying suggestions on deleted lines is not supported.You must change the existing code in this line in order to create a valid suggestion.Outdated suggestions cannot be applied.This suggestion has been applied or marked resolved.Suggestions cannot be applied from pending reviews.Suggestions cannot be applied on multi-line comments.Suggestions cannot be applied while the pull request is queued to merge.Suggestion cannot be applied right now. Please check back later.
Add hierarchy layout transforms wrapping d3-hierarchy: tree, treemap, pack, and partition.
treeNode()/treeLink()— tree and clusterlayouts (Closes feature: add Tree transform #81, Closes feature: Add treeLink transform #358, Closes feature: Add treeNode transform #359)
treemapNode()— space-filling treemap rectanglespackNode()— circle-packing layoutpartitionNode()/partitionLink()— icicle/sunburstrectangular partitions
All transforms use a curried factory pattern (
treeNode(options)({ data })) that produces new record sets compatible with existing marks (Dot, Link, Rect, Text). Paired *Node/*Link transforms share a WeakMap-based cache so the layout computes only once per data array.treeNode/treeLinkfollow the Observable Plot tree transform API.treemapNode,packNode, andpartitionNode/partitionLinkextend beyond Observable Plot's API, wrapping d3-hierarchy layouts directly.Partially addresses #92 (Tree mark) and #75 (missing transform types) — the transforms are implemented but a dedicated
<Tree>convenience mark is not included in this PR.What's included
hierarchy.ts):buildHierarchy()for path-based and id/parentId stratification,cachedLayout()for paired transform cachingflare.csvsample datasetd3-hierarchy+@types/d3-hierarchyDesign decisions
fn({data, ...channels})pattern used by stack/bin/group — hierarchy transforms produce entirely new record sets (nodes/links) rather than modifying existing channel data. This matches Observable Plot's approach.<Tree>mark — keeping this PR focused on transforms. A convenience mark that composes treeNode + treeLink + Dot + Link could follow as a separate PR.Test plan
pnpm test— 817 tests pass (95 files)pnpm lint— cleanpnpm check— 0 errorspnpm build— successful static build🤖 Generated with Claude Code