D3 Flextree – Resizable Nodes
by Rajesh Danabal
HTML
<!DOCTYPE html>
<meta charset="utf-8" />
<title>D3 Flextree – Resizable Nodes</title>
<style>
body {
margin: 0;
font-family: sans-serif;
background: #0b0f14;
color: #e6edf3;
}
svg {
width: 100vw;
height: 100vh;
display: block;
}
.node rect {
rx: 8;
ry: 8;
fill: #1f2937;
stroke: #94a3b8;
stroke-width: 1.25;
}
.node text {
fill: #e6edf3;
pointer-events: none;
font-size: 12px;
}
.handle {
fill: #93c5fd;
stroke: #1e3a8a;
stroke-width: 1;
cursor: nwse-resize;
}
.link {
fill: none;
stroke: #475569;
stroke-width: 1.25;
}
</style>
<body>
<svg id="svg"></svg>
<!-- D3 + d3-flextree -->
<script src="https://cdn.jsdelivr.net/npm/d3@7"></script>
<script src="https://cdn.jsdelivr.net/npm/d3-flextree@2"></script>
<script>
// ---------- Utilities ----------
const DEFAULT_W = 120;
const DEFAULT_H = 60;
function setDefaults(node, defaultW = DEFAULT_W, defaultH = DEFAULT_H) {
if (node.w == null) node.w = defaultW;
if (node.h == null) node.h = defaultH;
if (node.children)
node.children.forEach(c => setDefaults(c, defaultW, defaultH));
}
const getW = d =>
typeof d.data.w === "number" ? d.data.w : DEFAULT_W;
const getH = d =>
typeof d.data.h === "number" ? d.data.h : DEFAULT_H;
// ---------- Sample data ----------
const data = {
name: "Root",
w: 120,
h: 60,
children: [
{
name: "Alpha",
w: 120,
h: 60,
children: [
{ name: "A-1", w: 110, h: 50 },
{ name: "A-2", w: 140, h: 60 }
]
},
{ name: "Beta", w: 140, h: 70 },
{ name: "Gamma", w: 160, h: 60 }
]
};
setDefaults(data);
// ---------- Layout setup ----------
const hGap = 30;
const vGap = 30;
...