{"spec_id":"scatter-connected-temporal","library":"chartjs","language":"javascript","code":"// anyplot.ai\n// scatter-connected-temporal: Connected Scatter Plot with Temporal Path\n// Library: chartjs 4.4.7 | JavaScript 22.22.3\n// Quality: 92/100 | Created: 2026-06-09\n\nconst t = window.ANYPLOT_TOKENS;\n\n// CO₂ concentration (ppm) vs global temperature anomaly (°C), biennial 1970–2020\nconst climateData = [\n  { year: 1970, co2: 325.7, temp: 0.03 },\n  { year: 1972, co2: 327.5, temp: 0.04 },\n  { year: 1974, co2: 330.1, temp: -0.07 },\n  { year: 1976, co2: 332.1, temp: -0.10 },\n  { year: 1978, co2: 335.5, temp: 0.05 },\n  { year: 1980, co2: 338.7, temp: 0.26 },\n  { year: 1982, co2: 341.1, temp: 0.12 },\n  { year: 1984, co2: 344.4, temp: 0.16 },\n  { year: 1986, co2: 347.2, temp: 0.17 },\n  { year: 1988, co2: 351.3, temp: 0.39 },\n  { year: 1990, co2: 354.4, temp: 0.44 },\n  { year: 1992, co2: 356.4, temp: 0.22 },\n  { year: 1994, co2: 358.9, temp: 0.31 },\n  { year: 1996, co2: 362.7, temp: 0.33 },\n  { year: 1998, co2: 366.7, temp: 0.61 },\n  { year: 2000, co2: 369.5, temp: 0.33 },\n  { year: 2002, co2: 373.2, temp: 0.56 },\n  { year: 2004, co2: 377.5, temp: 0.48 },\n  { year: 2006, co2: 381.9, temp: 0.61 },\n  { year: 2008, co2: 385.6, temp: 0.43 },\n  { year: 2010, co2: 389.9, temp: 0.72 },\n  { year: 2012, co2: 394.0, temp: 0.64 },\n  { year: 2014, co2: 397.2, temp: 0.75 },\n  { year: 2016, co2: 403.9, temp: 1.01 },\n  { year: 2018, co2: 408.5, temp: 0.83 },\n  { year: 2020, co2: 414.2, temp: 1.02 },\n];\n\nconst n = climateData.length;\n\n// Parse hex to [r, g, b]\nfunction hexToRgb(hex) {\n  return [\n    parseInt(hex.slice(1, 3), 16),\n    parseInt(hex.slice(3, 5), 16),\n    parseInt(hex.slice(5, 7), 16),\n  ];\n}\n\n// Temporal gradient: Imprint brand green → Imprint blue (via t.seq)\nconst [r1, g1, b1] = hexToRgb(t.seq[0]);\nconst [r2, g2, b2] = hexToRgb(t.seq[1]);\n\nfunction lerpColor(frac) {\n  const r = Math.round(r1 + (r2 - r1) * frac);\n  const g = Math.round(g1 + (g2 - g1) * frac);\n  const b = Math.round(b1 + (b2 - b1) * frac);\n  return `rgb(${r},${g},${b})`;\n}\n\nconst pointColors = climateData.map((_, i) => lerpColor(i / (n - 1)));\nconst pointRadius = climateData.map((_, i) => (i === 0 || i === n - 1 ? 11 : 6));\nconst lineColor = `rgba(${r1},${g1},${b1},0.45)`;\n\nconst labelYears = new Set([1970, 1980, 1990, 2000, 2010, 2020]);\n\n// Fill canvas background before chart renders\nChart.register({\n  id: \"canvasBg\",\n  beforeDraw(chart) {\n    const ctx = chart.ctx;\n    ctx.save();\n    ctx.fillStyle = t.pageBg;\n    ctx.fillRect(0, 0, chart.width, chart.height);\n    ctx.restore();\n  },\n});\n\n// Draw year labels above annotated key points\nChart.register({\n  id: \"temporalLabels\",\n  afterDatasetsDraw(chart) {\n    const ctx = chart.ctx;\n    const meta = chart.getDatasetMeta(0);\n    ctx.save();\n    ctx.font = \"bold 14px system-ui, sans-serif\";\n    ctx.textAlign = \"center\";\n    ctx.textBaseline = \"bottom\";\n    ctx.fillStyle = t.inkSoft;\n    climateData.forEach((d, i) => {\n      if (!labelYears.has(d.year)) return;\n      const pt = meta.data[i];\n      if (!pt) return;\n      ctx.fillText(String(d.year), pt.x, pt.y - 14);\n    });\n    ctx.restore();\n  },\n});\n\n// Mount\nconst canvas = document.createElement(\"canvas\");\ndocument.getElementById(\"container\").appendChild(canvas);\n\n// Chart\nnew Chart(canvas, {\n  type: \"scatter\",\n  data: {\n    datasets: [\n      {\n        label: \"CO₂ vs Temperature\",\n        data: climateData.map(d => ({ x: d.co2, y: d.temp })),\n        showLine: true,\n        borderColor: lineColor,\n        borderWidth: 2,\n        pointBackgroundColor: pointColors,\n        pointBorderColor: t.pageBg,\n        pointBorderWidth: 1.5,\n        pointRadius,\n        pointHoverRadius: pointRadius.map(r => r + 2),\n        tension: 0,\n      },\n    ],\n  },\n  options: {\n    responsive: true,\n    maintainAspectRatio: false,\n    animation: false,\n    plugins: {\n      title: {\n        display: true,\n        text: \"scatter-connected-temporal · javascript · chartjs · anyplot.ai\",\n        color: t.ink,\n        font: { size: 22, weight: \"600\" },\n        padding: { top: 20, bottom: 8 },\n      },\n      subtitle: {\n        display: true,\n        text: \"Color encodes time: 1970 (green) → 2020 (blue)\",\n        color: t.inkSoft,\n        font: { size: 14 },\n        padding: { bottom: 16 },\n      },\n      legend: { display: false },\n    },\n    scales: {\n      x: {\n        title: {\n          display: true,\n          text: \"CO₂ Concentration (ppm)\",\n          color: t.ink,\n          font: { size: 16 },\n        },\n        ticks: { color: t.inkSoft, font: { size: 14 } },\n        grid: { color: t.grid },\n      },\n      y: {\n        title: {\n          display: true,\n          text: \"Temperature Anomaly (°C)\",\n          color: t.ink,\n          font: { size: 16 },\n        },\n        ticks: { color: t.inkSoft, font: { size: 14 } },\n        grid: { color: t.grid },\n      },\n    },\n    layout: {\n      padding: { top: 10, right: 50, bottom: 20, left: 20 },\n    },\n  },\n});\n"}