Skip to main content

Function: shotZones()

shotZones(areas, o): Markish[]

Defined in: packages/sdvplot/src/plot/shots.ts:303

sporty's zone areas (built with scale: 10, legacy tenths) filled per zone, plus optional haloed labels, the corner strips' set vertically (blazing-the-nets main zones mode, lib/charts/hexShotChart.ts:97-136). Each area's path carries data-sdv-id = its zone.

Returns the zone paths, then the labels (with text), then the tip (with tip). Marks paint in array order and the tip is last, so spread these marks LAST, or add other marks before them: a mark added after them paints over the tip. After ...court.marks the zone fills dim the court lines under them; main draws its lines after the zones, but moving the court mark last would hide the zones under its floor (sporty draws lines as filled polygons). For lines on top, put a second surface right after the paths, its colorUpdates setting plot_background, defensive_half_court, offensive_half_court, court_apron, two_point_range, painted_area, center_circle_fill and free_throw_circle_fill to "#00000000" so only the lines remain: const [paths, ...rest] = shotZones(areas, o), then marks: [...court.marks, paths, ...lines.marks, ...rest]. The areas are the mark's data and each path is named by its zone (with text, then its label's text). tip: true adds a Plot.tip mark that names the zone under the pointer and, with stats (statsByZone(shots)), its makes/attempts and FG%. It follows the nearest of a grid of anchors inside the zones (a fortieth of their extent apart, 1.25 ft on an NBA half court), so within about that of a zone edge it may name the neighbour. The tip's data is the areas, so channels (shown in the tip) read the caller's fields; a tip object's format overrides sdvplot's key by key. Every other Plot.geo option passes through to the zone paths.

Parameters​

areas​

readonly BasketballZoneArea[]

o​

ShotZonesOptions

Returns​

Markish[]

Example​

import * as Plot from "@observablehq/plot";
import { basketballZones } from "@sportsdataverse/sporty";
import { shotZones, surface } from "@sportsdataverse/sdvplot/plot";

const court = surface("nba", { displayRange: "defense" });
const zones = shotZones(basketballZones("nba", { scale: 10 }), { fill: () => "#f7f7f7", text: (z) => z });
Plot.plot({ ...court.scales, marks: [...court.marks, ...zones] });