Command Palette

Search for a command to run...

Hectal
Back to the lesson: Topic 14.2 — The Exceptions: Axes, Brushes, Zoom and Transitions
Data Visualization · Example 1 of 2

Three axes in StrictMode, and listeners that leak

Run it, then add a second effect run by hand in your head: StrictMode already did it for you. Only the version that appends is wrong, and only the leaky component outlives its unmount. The numbers are counts of real DOM nodes and real listeners.

Some D3 helpers must write into the page: axes, brushes, zoom and transitions. Give each one an element that React renders empty, hand it over through a ref, run it in an effect, and always return a cleanup. Then StrictMode's double effect is harmless.

Change the code and press Run (Ctrl+Enter). Predict what will happen first, then break it on purpose and read what changes. Your edits are saved and match the lesson page.

Ready for more? This phase has 5 hands-on exercises with automatic checks.

Practice questions

Write the code in the editor, run it, then open the model answer to compare.

01

Write an Axis component for a bottom axis that takes a scale prop, calls d3.axisBottom in an effect, and leaves the <g> empty again on cleanup. Why does it list [scale] as its dependency?

02

A teammate's Brush component adds d3.brushX() to a <g> in an effect and never removes it. Describe two problems this causes, and fix the effect.

Explain it without notes

01

Why does React's StrictMode run effects twice, and what kind of bug does that expose in a D3 chart?

02

What is the difference between selection.call(axis) and selection.append("g").call(axis) inside an effect?

03

Which part of a zoomable chart should live in React state, and why derive the scale instead of changing it?

04

When is it better to draw the axis as JSX than with d3.axisBottom?

Three axes in StrictMode, and listeners that leak

Preview

Press Run to see the page.

Console

Nothing logged yet.

Expected console output

append: effect ran 2 times -> 10 ticks, 2 axis line(s)
call:   effect ran 2 times -> 5 ticks, 1 axis line(s)
jsx:    no effect          -> 5 ticks, 1 axis line(s)
Tidy  resize listeners while mounted: 1 | after unmount: 0
Leaky resize listeners while mounted: 2 | after unmount: 2