DEV Community

Alex Spinov
Alex Spinov

Posted on

D3.js Has a Free API That Goes Way Beyond Bar Charts

D3.js is the most powerful data visualization library ever created. Most developers only use it for charts, but its modular API covers everything from geography to physics simulations.

D3-Selection: jQuery for Data

import { select, selectAll } from "d3-selection";

// Bind data to DOM elements
const bars = select("svg")
  .selectAll("rect")
  .data(dataset)
  .join(
    enter => enter.append("rect")
      .attr("x", (d, i) => i * 30)
      .attr("height", 0)
      .attr("fill", "steelblue")
      .call(enter => enter.transition().duration(750)
        .attr("height", d => yScale(d.value))
        .attr("y", d => height - yScale(d.value))),
    update => update
      .call(update => update.transition().duration(750)
        .attr("height", d => yScale(d.value))),
    exit => exit
      .call(exit => exit.transition().duration(500)
        .attr("height", 0)
        .remove())
  );
Enter fullscreen mode Exit fullscreen mode

D3-Scale: Map Any Domain to Any Range

import { scaleLinear, scaleTime, scaleBand, scaleOrdinal } from "d3-scale";
import { schemeTableau10 } from "d3-scale-chromatic";

// Numbers → pixels
const yScale = scaleLinear().domain([0, maxValue]).range([height, 0]).nice();

// Dates → pixels
const xScale = scaleTime()
  .domain([new Date("2024-01-01"), new Date("2026-12-31")])
  .range([0, width]);

// Categories → colors
const colorScale = scaleOrdinal(schemeTableau10);

// Categories → bands (bar charts)
const bandScale = scaleBand()
  .domain(categories)
  .range([0, width])
  .padding(0.2);
Enter fullscreen mode Exit fullscreen mode

D3-Geo: Map the World

import { geoPath, geoMercator, geoNaturalEarth1 } from "d3-geo";
import { json } from "d3-fetch";
import { feature } from "topojson-client";

const world = await json("https://cdn.jsdelivr.net/npm/world-atlas@2/countries-110m.json");
const countries = feature(world, world.objects.countries);

const projection = geoNaturalEarth1().fitSize([width, height], countries);
const path = geoPath(projection);

svg.selectAll("path")
  .data(countries.features)
  .join("path")
  .attr("d", path)
  .attr("fill", d => colorScale(d.properties.scraped_count));
Enter fullscreen mode Exit fullscreen mode

D3-Force: Physics Simulations

import { forceSimulation, forceLink, forceManyBody, forceCenter, forceCollide } from "d3-force";

const simulation = forceSimulation(nodes)
  .force("link", forceLink(links).id(d => d.id).distance(100))
  .force("charge", forceManyBody().strength(-300))
  .force("center", forceCenter(width / 2, height / 2))
  .force("collide", forceCollide(30))
  .on("tick", () => {
    nodeElements.attr("cx", d => d.x).attr("cy", d => d.y);
    linkElements.attr("x1", d => d.source.x).attr("y1", d => d.source.y)
      .attr("x2", d => d.target.x).attr("y2", d => d.target.y);
  });
Enter fullscreen mode Exit fullscreen mode

D3-Hierarchy: Trees and Treemaps

import { hierarchy, treemap, treemapSquarify } from "d3-hierarchy";

const root = hierarchy(data)
  .sum(d => d.value)
  .sort((a, b) => b.value - a.value);

const layout = treemap()
  .size([width, height])
  .padding(2)
  .tile(treemapSquarify);

layout(root);

svg.selectAll("rect")
  .data(root.leaves())
  .join("rect")
  .attr("x", d => d.x0)
  .attr("y", d => d.y0)
  .attr("width", d => d.x1 - d.x0)
  .attr("height", d => d.y1 - d.y0);
Enter fullscreen mode Exit fullscreen mode

Visualize scraped data with D3? My Apify tools deliver structured datasets ready for visualization.

Custom data visualization? Email spinov001@gmail.com

Top comments (0)