Published
Edited
Dec 16, 2020
Insert cell
Insert cell
Insert cell
Insert cell
Insert cell
Insert cell
Insert cell
Insert cell
render_data_table(table_info)
Insert cell
Insert cell
// county/country data
// filter for food
// zoom in and out for geographic
// hover over region for more info

//OR
// zoomable scatter plot of crop production
// filter by year
// hover over to see which country
Insert cell
data = d3.csvParse(await FileAttachment("pokemon.csv").text(), d3.autoType)
Insert cell
x_variable = "Attack"
Insert cell
y_variable = "Special Attack"
Insert cell
legendary = "Legendary"
Insert cell
extent_atk = d3.extent(data, d => +d["Attack"])
Insert cell
extent_sp_atk = d3.extent(data, d => +d["Sp. Atk"])
Insert cell
uniq_legend = _.uniqBy(data.map(d => d["Type 1"]))
Insert cell
margin = ({ top: 20, right: 30, bottom: 30, left: 40 })
Insert cell
width = 954
Insert cell
height = 500
Insert cell
xScale = d3
.scaleLinear()
.domain(extent_atk)
.range([margin.left, width - margin.right])
Insert cell
yScale = d3
.scaleLinear()
.domain(extent_sp_atk)
.range([height - margin.bottom, margin.top])
Insert cell
colorScale = d3.scaleOrdinal(uniq_legend, d3.schemePaired)
Insert cell
xAxis = g =>
g
.attr("transform", `translate(0,${height - margin.bottom})`)
.call(d3.axisBottom(xScale))
Insert cell
yAxis = g =>
g.attr("transform", `translate(${margin.left},0)`).call(d3.axisLeft(yScale))
Insert cell
type_legend = legend({ color: colorScale, title: "Type 1", width: 900 })
Insert cell
filteredData = data.filter(d => d["Type 1"] == type || d["Type 2"] == type)
Insert cell
Insert cell
{
const svg = d3
.create("svg")
.attr("viewBox", [-100, -100, width + 200, height + 200]);
const gx = svg
.append("g")
.attr("class", "x-axis")
.attr("transform", "translate(30, 0)")
.call(d3.axisLeft().scale(yScale));
const gy = svg
.append("g")
.attr("class", "y-axis")
.attr("transform", "translate(0, 480)")
.call(d3.axisBottom().scale(xScale));

const tooltip = d3
.select("#tooltip")
.append("div")
.style("opacity", 0)
.attr("class", "tooltip")
.style("background-color", "black")
.style("border-radius", "5px")
.style("padding", "10px")
.style("color", "white");

const showTooltip = function(d) {
tooltip.transition().duration(100);
tooltip
.style("opacity", 1)
.html("Name: " + d.Name)
//.html("Attack: " + d["Attack"])
//.html("Sp. Attack: " + d["Sp. Atk"])
//.html("Legendary: " + d["Legendary"])
.style("left", d3.mouse(this)[0] + 40 + "px")
.style("top", d3.mouse(this)[1] + 40 + "px");
};
const moveTooltip = function(d) {
tooltip
.style("left", d3.mouse(this)[0] + 40 + "px")
.style("top", d3.mouse(this)[1] + 40 + "px");
};
const hideTooltip = function(d) {
tooltip
.transition()
.duration(200)
.style("opacity", 0);
};

svg
.append("g")
.attr("stroke-width", 1.5)
.selectAll("dot")
.data(filteredData)
.enter()
.append("circle")
.attr("cx", d => xScale(d["Attack"]))
.attr("cy", d => yScale(d["Sp. Atk"]))
.attr("fill", d => colorScale(d["Type 1"]))
.attr("r", 7)
.on("mouseover", showTooltip)
.on("mousemove", moveTooltip)
.on("mouseleave", hideTooltip);

svg
.append("text")
.style("text-anchor", "middle")
.attr("x", 500)
.attr("y", -20)
.text("Attack vs Special Attack Power of Pokemon");
svg
.append("text")
.attr("class", "x label")
.attr("text-anchor", "middle")
.attr("x", width / 2)
.attr("y", height + 30)
.text("Attack");
svg
.append("text")
.attr("class", "y label")
.attr("text-anchor", "end")
.attr("x", -200)
.attr("y", -20)
.attr("transform", "rotate(-90)")
.text("Special Attack");

svg
.append("g")
.append(() => type_legend)
.attr("x", 50)
.attr("y", 550);

function zoomed({ transform }) {
const zx = transform.rescaleX(xScale).interpolate(d3.interpolateRound);
const zy = transform.rescaleY(yScale).interpolate(d3.interpolateRound);
svg.selectAll("circle").attr("transform", transform);
gx.call(xAxis, zx);
gy.call(yAxis, zy);
}

const zoom = d3
.zoom()
.scaleExtent([0.5, 32])
.on("zoom", zoomed);

svg.call(zoom).call(zoom.transform, d3.zoomIdentity);

return svg.node();
}
Insert cell
Insert cell
Insert cell
Insert cell
Insert cell
Insert cell
Insert cell
d3 = require("d3")
Insert cell
_ = require("lodash")
Insert cell
import { swatches, legend } from "@d3/color-legend"
Insert cell
import { select } from "@jashkenas/inputs"
Insert cell
Insert cell

Purpose-built for displays of data

Observable is your go-to platform for exploring data and creating expressive data visualizations. Use reactive JavaScript notebooks for prototyping and a collaborative canvas for visual data exploration and dashboard creation.
Learn more