{"id":"3600af71d27123f4","slug":"sunrise-and-sunset-worldwide","trashed":false,"description":"","likes":9,"publish_level":"public","forks":2,"fork_of":null,"has_importers":true,"update_time":"2020-05-27T05:53:27.996Z","first_public_version":null,"paused_version":null,"publish_time":"2019-12-06T10:28:46.818Z","publish_version":1401,"latest_version":1401,"thumbnail":"13a1f810e043d7809a97421dabe1c9ee5ca57f7f8e482c16d74a5794927d75ad","default_thumbnail":"13a1f810e043d7809a97421dabe1c9ee5ca57f7f8e482c16d74a5794927d75ad","roles":[],"sharing":null,"owner":{"id":"512cbe7209990c30","avatar_url":"https://avatars.observableusercontent.com/avatar/fa4015f63c3a56af76b90247b0b0f8a98019b671f135157d746d3924eda27c07","login":"asg017","name":"Alex Garcia","bio":"Software engineer, available for freelance work! • he/him/his","home_url":"https://alexgarcia.xyz","type":"team","tier":"starter_2024"},"creator":{"id":"113fc3dc69e1f893","avatar_url":"https://avatars.observableusercontent.com/avatar/fa4015f63c3a56af76b90247b0b0f8a98019b671f135157d746d3924eda27c07","login":"asg017","name":"Alex Garcia","bio":"Software engineer, available for freelance work! • he/him/his","home_url":"https://alexgarcia.xyz","tier":"pro"},"authors":[{"id":"113fc3dc69e1f893","avatar_url":"https://avatars.observableusercontent.com/avatar/fa4015f63c3a56af76b90247b0b0f8a98019b671f135157d746d3924eda27c07","name":"Alex Garcia","login":"asg017","bio":"Software engineer, available for freelance work! • he/him/his","home_url":"https://alexgarcia.xyz","tier":"pro","approved":true,"description":""}],"collections":[],"files":[{"id":"0048b8f01872b01b671845da8adeb8dfa27244f2f983846cb41cd78afc5c653c9ff8c4724698f72d5ba11875a17d9db6bc8c3f66225b5fcf860ba7f369283ead","url":"https://static.observableusercontent.com/files/0048b8f01872b01b671845da8adeb8dfa27244f2f983846cb41cd78afc5c653c9ff8c4724698f72d5ba11875a17d9db6bc8c3f66225b5fcf860ba7f369283ead","download_url":"https://static.observableusercontent.com/files/0048b8f01872b01b671845da8adeb8dfa27244f2f983846cb41cd78afc5c653c9ff8c4724698f72d5ba11875a17d9db6bc8c3f66225b5fcf860ba7f369283ead?response-content-disposition=attachment%3Bfilename*%3DUTF-8%27%27moment-timezone-0.5.27.js","name":"moment-timezone-0.5.27.js","create_time":"2019-12-05T23:13:18.490Z","mime_type":"application/javascript","status":"public","size":239557,"content_encoding":"gzip","private_bucket_id":null},{"id":"0ca9148938fe656b24d3cd9474fc7190de67f0c2fa0c6940f93f874da1572341e3691665fd40b708cdd5573317e4b18f96bfc1d3617464cb0dc2d8b607c3bddd","url":"https://static.observableusercontent.com/files/0ca9148938fe656b24d3cd9474fc7190de67f0c2fa0c6940f93f874da1572341e3691665fd40b708cdd5573317e4b18f96bfc1d3617464cb0dc2d8b607c3bddd","download_url":"https://static.observableusercontent.com/files/0ca9148938fe656b24d3cd9474fc7190de67f0c2fa0c6940f93f874da1572341e3691665fd40b708cdd5573317e4b18f96bfc1d3617464cb0dc2d8b607c3bddd?response-content-disposition=attachment%3Bfilename*%3DUTF-8%27%27world-atlast-1-110m.json","name":"world-atlast-1-110m.json","create_time":"2019-12-06T09:41:09.683Z","mime_type":"application/json","status":"public","size":102116,"content_encoding":"gzip","private_bucket_id":null}],"comments":[],"commenting_lock":null,"suggestion_from":null,"suggestions_to":[],"version":1401,"title":"Sunrise and Sunset - Worldwide","license":null,"copyright":"","nodes":[{"id":0,"value":"md`# Sunrise and Sunset - Worldwide\n\nI loved [this reddit post](https://www.reddit.com/r/dataisbeautiful/comments/e6fc7r/oc_i_got_inspired_by_the_sunrise_and_sunset_post/) from [u/ettpinktnoll](https://www.reddit.com/user/ettpunktnoll/), so I made this notebook where you can create your own Sunrise/Sunset animation, from (almost) any point in the world!`","pinned":false,"mode":"js","data":null,"name":null},{"id":1338,"value":"viewof timeI = Scrubber(times.map((_, i) => i), {\n  format: i =>\n    times[i].day.toLocaleString(\"en\", { month: \"long\", day: \"numeric\" }),\n  loop: true\n})","pinned":false,"mode":"js","data":null,"name":null},{"id":20,"value":"graphic = {\n  const svg = d3.select(DOM.svg(width, height));\n  const g = svg.append('g');\n\n  const updateBackground = background(svg);\n  const updateDateLabel = dateLabel(svg);\n  const updateAxis = axis(svg);\n  const updateSunBar = sunBar(svg);\n  const updateTotal = totalLabel(svg);\n  const updateSunriseLabel = sunriseLabel(svg);\n  const updateSunsetLabel = sunsetLabel(svg);\n  drawWorld(svg);\n\n  x.domain([0, 60 * 60 * 24]);\n  invalidation.then(() => svg.interrupt());\n  return Object.assign(svg.node(), {\n    update(time) {\n      const transition = svg\n        .transition()\n        .duration((1000 / 60) * 3)\n        .ease(d3.easeLinear);\n\n      updateBackground(time, transition);\n      updateAxis(time, transition);\n      updateSunBar(time, transition);\n      updateDateLabel(time, transition);\n      updateTotal(time, transition);\n      updateSunriseLabel(time, transition);\n      updateSunsetLabel(time, transition);\n    }\n  });\n}","pinned":false,"mode":"js","data":null,"name":null},{"id":236,"value":"viewof coordinates = worldMapCoordinates({\n  title: 'Location',\n  description: 'Change the location of the animation by clicking on this map!',\n  value: params.has('location')\n    ? JSON.parse(params.get('location'))\n    : [-122.27, 37.87],\n  width\n})","pinned":false,"mode":"js","data":null,"name":null},{"id":815,"value":"md`[Direct Link](${\n  document.baseURI.split(/[?#]/)[0]\n}?location=${encodeURIComponent(\n  JSON.stringify(coordinates)\n)}) for this location (\\`${coordsFormat(coordinates)}\\`)`","pinned":false,"mode":"js","data":null,"name":null},{"id":1350,"value":"controller = graphic.update(time)","pinned":true,"mode":"js","data":null,"name":null},{"id":1328,"value":"md`## Credits\n\nThanks to @mbostock for many D3 examples and for [bar chart race](https://observablehq.com/@d3/bar-chart-race-explained) (where I modeled the animation pattern after), [Vladimir Agafonkin](https://agafonkin.com/) for [Suncalc](https://github.com/mourner/suncalc), and reddit user [u/ettpinktnoll](https://www.reddit.com/user/ettpunktnoll/) for the original animation design.`","pinned":false,"mode":"js","data":null,"name":null},{"id":804,"value":"md`## Improve this graphic!\n\nThis graphic isn't perfect yet - feel free to send in [suggestions](https://observablehq.com/@observablehq/suggestions-and-comments) to improve it!\n\n### \"Sun don't set, Sun don't rise\"\n\nIn some places, notable the most northern or southern parts of the world, sometimes the sun doesn't do what you think it *should* do. Here are the 4 problems that can come up, that this graphic doesn't currently handle:\n\n1. Sun did not set - the sun rose and didn't set during for a given day (\\`sunset === Invalid Date\\`)\n2. Sun did not rise - the sun set and didn't rise during for a given day (\\`sunrise === Invalid Date\\`)\n3. Sun did not rise or set, and the sun wasn't out at all (\\`sunset === Invalid Date && sunrise === Invalid Date\\`, and the last \"sun event\" was a sunset)\n4. Sun did not rise or set, and the sun was out all day (\\`sunset === Invalid Date && sunrise === Invalid Date\\`, and the last \"sun event\" was a sunrise)\n\n### Label Conflicts\n\nIf there is very little sun (2 hrs or so), the yellow sun block is so small that the \"Total Sun\" label overflows weirdly, and the sunrise/sunset labels smash into each other. [Example](https://observablehq.com/d/3600af71d27123f4?location=%5B-44.09%2C66.67%5D).\n\n\n### Search by Names\n\nPointing on a map is difficult and not familiar, but having a search box where people could lookup \"Los Angeles\" or \"Mexico City\" and geocode that into lat/lon would be great!\n\n### Geocode Coordinates\n\nGiven the lat/lon, get a \"friendly\" address for that location. Maybe by country/state/municipality/ocean?\n`","pinned":false,"mode":"js","data":null,"name":null},{"id":846,"value":"md`---\n\n## Appendix`","pinned":false,"mode":"js","data":null,"name":null},{"id":1382,"value":"time = times[timeI]","pinned":false,"mode":"js","data":null,"name":null},{"id":78,"value":"function sunBar(svg) {\n  const g = svg\n    .append('g')\n    .classed('sunbar', true)\n    .attr('transform', `translate(${margin.left},${sunMargins.top})`);\n\n  const sunrise = g.append('path').attr('fill', colors.YELLOW);\n  const sun = g.append('path').attr('fill', colors.DARKYELLOW);\n  const sunset = g.append('path').attr('fill', colors.YELLOW);\n\n  const lRect = g\n    .append('rect')\n    .attr('x', 0)\n    .attr('y', 0)\n    .attr('fill', colors.YELLOW)\n    .attr('height', height - sunMargins.top - sunMargins.bottom - 10);\n  const rRect = g\n    .append('rect')\n    .attr('x', 0)\n    .attr('y', 0)\n    .attr('fill', colors.YELLOW)\n    .attr('height', height - sunMargins.top - sunMargins.bottom - 10);\n\n  return (time, transition) => {\n    const draw = drawSun(time);\n    sunrise.transition(transition).attr('d', draw.sunrise(d3.path()));\n    sun.transition(transition).attr('d', draw.sun(d3.path()));\n    sunset.transition(transition).attr('d', draw.sunset(d3.path()));\n  };\n}","pinned":false,"mode":"js","data":null,"name":null},{"id":38,"value":"function axis(svg) {\n  const g = svg\n    .append('g')\n    .classed('axis', true)\n    .attr(\n      'transform',\n      `translate(${margin.left}, ${height - margin.bottom - 10})`\n    )\n    .attr('fill', 'white')\n    .attr('stroke', 'white');\n\n  g.append('rect')\n    .attr('x', 0)\n    .attr('y', 0)\n    .attr('width', x(60 * 60 * 24))\n    .attr('height', 2);\n\n  g.append('text')\n    .attr('x', 0)\n    .attr('dy', '1.5rem')\n    .attr('text-anchor', 'middle')\n    .text('00:00');\n\n  g.append('text')\n    .attr('x', x(60 * 60 * 24))\n    .attr('dy', '1.5rem')\n    .attr('text-anchor', 'middle')\n    .text('23:59');\n\n  return (_, transition) => {};\n}","pinned":false,"mode":"js","data":null,"name":null},{"id":143,"value":"function totalLabel(svg) {\n  const g = svg.append('g').attr('text-anchor', 'middle');\n\n  g.append('text')\n    .text('Total Sun')\n    .attr('font-size', '.9rem');\n  const durationSpan = g\n    .append('text')\n    .attr('dy', '2.25rem')\n    .attr('font-size', '2.5rem')\n    .attr('font-weight', 600);\n  return (t, transition) => {\n    const rise = x(getSecondsInDay(t.localSunrise));\n\n    const set = x(\n      getSecondsInDay(\n        t.localSunset.getDay() !== t.localSunrise.getDay()\n          ? m(t.localSunset)\n              .subtract(1, 'day')\n              .toDate()\n          : t.localSunset\n      )\n    );\n    const midnight = x(60 * 60 * 24);\n    const xPos =\n      t.localSunset.getDay() === t.localSunrise.getDay()\n        ? (set - rise) / 2 + rise\n        : midnight - rise > set - x(0)\n        ? (midnight - rise) / 2 + rise\n        : (set - x(0)) / 2 + x(0);\n    g.transition(transition).attr(\n      'transform',\n      `translate(${margin.left + xPos},${sunMargins.top + 100})`\n    );\n    const seconds =\n      t.localSunset.getDay() === t.localSunrise.getDay()\n        ? getSecondsInDay(t.localSunset) - getSecondsInDay(t.localSunrise)\n        : 60 * 60 * 24 -\n          getSecondsInDay(t.localSunrise) +\n          getSecondsInDay(t.localSunset);\n\n    const hrs = Math.floor(seconds / 60 / 60);\n    const mins = Math.floor((seconds - hrs * 60 * 60) / 60);\n    durationSpan.text(`${hrs}:${mins < 10 ? '0' : ''}${mins}`);\n  };\n}","pinned":false,"mode":"js","data":null,"name":null},{"id":973,"value":"function drawWorld(svg) {\n  const projection = d3\n    .geoNaturalEarth1()\n    .precision(0.1)\n    .fitSize([250, 250], { type: \"Sphere\" });\n  const path = d3.geoPath(projection).pointRadius(2.5);\n  const g = svg\n    .append('g')\n    .attr(\n      'transform',\n      `translate(${width - margin.right - 230}, ${margin.top - 75})`\n    )\n    .classed('world', true);\n  g.append('path')\n    .attr('stroke', 'rgba(255,255,255,25%)')\n    .attr('fill', 'none')\n    .attr('d', path(d3.geoGraticule10()));\n\n  g.selectAll('.land')\n    .data(topojson.feature(world, world.objects.land).features)\n    .join('path')\n    .classed('land', true)\n    .attr('fill', colors.LIGHTBLUE)\n    .attr('d', path);\n\n  g.append('circle')\n    .attr('cx', projection(coordinates)[0])\n    .attr('cy', projection(coordinates)[1])\n    .attr('r', 8)\n    .attr('fill', 'red');\n}","pinned":false,"mode":"js","data":null,"name":null},{"id":149,"value":"function sunriseLabel(svg) {\n  const g = svg\n    .append('g')\n    .attr('fill', 'white')\n    .attr('text-anchor', 'middle');\n\n  g.append('text').text('Sunrise');\n\n  const time = g\n    .append('text')\n    .attr('dy', '1.75rem')\n    .attr('font-size', '1.75rem')\n    .attr('font-weight', 700);\n\n  return (t, transition) => {\n    g.transition(transition).attr(\n      'transform',\n      `translate(${margin.left + x(getSecondsInDay(t.localSunrise))},${height -\n        margin.bottom -\n        50})`\n    );\n    time.text(formatTime(t.localSunrise));\n  };\n}","pinned":false,"mode":"js","data":null,"name":null},{"id":159,"value":"function sunsetLabel(svg) {\n  const g = svg\n    .append('g')\n    .attr('fill', 'white')\n    .attr('text-anchor', 'middle');\n  g.append('text').text('Sunset');\n\n  const time = g\n    .append('text')\n    .attr('dy', '1.75rem')\n    .attr('font-size', '1.75rem')\n    .attr('font-weight', 700);\n\n  return (t, transition) => {\n    const { sunset } = t;\n    g.attr(\n      'transform',\n      `translate(${margin.left + x(getSecondsInDay(t.localSunset))},${height -\n        margin.bottom -\n        50})`\n    );\n    time.text(formatTime(t.localSunset));\n  };\n}","pinned":false,"mode":"js","data":null,"name":null},{"id":58,"value":"function dateLabel(svg) {\n  const progressWidth = 220;\n  const g = svg\n    .append('g')\n    .classed('dateLabel', true)\n    .attr('transform', `translate(${margin.left},${margin.top})`)\n    .style('fill', 'white')\n    .attr('text-anchor', 'start');\n\n  const progress = g\n    .append('rect')\n    .attr('x', 0)\n    .attr('y', '0')\n    .attr('height', 2)\n    .attr('fill', 'white');\n  g.append('rect')\n    .attr('x', 0)\n    .attr('y', '0')\n    .attr('height', 1)\n    .attr('width', progressWidth)\n    .attr('fill', '#999');\n\n  const t = g\n    .append('text')\n    .attr('font-size', '3rem')\n    .attr('alignment-baseline', \"hanging\")\n    .attr('font-weight', 700);\n  g.append('text')\n    .attr('dy', '3rem')\n    .attr('font-size', '.9rem')\n    .attr('alignment-baseline', \"hanging\")\n    .text(`* ${timezoneName} timezone`);\n\n  return (time, transition) => {\n    t.text(formatDate(d3.timeDay(time.day)));\n    progress\n      .transition(transition)\n      .attr('width', (m(time.localSunrise).dayOfYear() / 365) * progressWidth);\n  };\n}","pinned":false,"mode":"js","data":null,"name":null},{"id":48,"value":"function background(svg) {\n  svg\n    .append('rect')\n    .attr('x', 0)\n    .attr('y', 0)\n    .attr('width', width)\n    .attr('height', height)\n    .attr('fill', colors.DARKBLUE);\n  return (time, transition) => {};\n}","pinned":false,"mode":"js","data":null,"name":null},{"id":547,"value":"function drawSun(time) {\n  const h = height - sunMargins.top - sunMargins.bottom - 60;\n  if (time.localSunset.getDay() !== time.localSunrise.getDay()) {\n    const rise = x(getSecondsInDay(time.localSunrise));\n    const set = x(\n      getSecondsInDay(\n        m(time.localSunset)\n          .subtract(1, 'day')\n          .toDate()\n      )\n    );\n    return {\n      sunrise(context) {\n        return context;\n      },\n      sun(context) {\n        context.moveTo(rise, 0);\n        context.lineTo(x(60 * 60 * 24), 0);\n        context.lineTo(x(60 * 60 * 24), h);\n\n        context.lineTo(rise, h);\n        context.closePath();\n\n        context.moveTo(x(0), 0);\n        context.lineTo(set, 0);\n        context.lineTo(set, h);\n        context.lineTo(x(0), h);\n        context.closePath();\n        return context;\n      },\n      sunset(context) {\n        return context;\n      }\n    };\n  }\n\n  const rise = x(getSecondsInDay(time.localDawn));\n  const riseEnd = x(getSecondsInDay(time.localSunriseEnd));\n\n  const setStart = x(getSecondsInDay(time.localSunset));\n  const set = x(getSecondsInDay(time.localDusk));\n\n  const midnight = x(60 * 60 * 24);\n  return {\n    sunrise(context) {\n      const l =\n        time.localSunriseEnd.getDay() === time.localDawn.getDay() ? rise : x(0);\n      context.moveTo(l, h);\n      context.bezierCurveTo(l, 0, l, 0, riseEnd, 0);\n      context.lineTo(riseEnd, h);\n      context.closePath();\n      return context;\n    },\n    sun(context) {\n      context.moveTo(riseEnd, 0);\n      context.lineTo(setStart, 0);\n      context.lineTo(setStart, h);\n      context.lineTo(riseEnd, h);\n      context.closePath();\n      return context;\n    },\n    sunset(context) {\n      const r =\n        time.localSunset.getDay() === time.localDusk.getDay() ? set : midnight;\n      context.moveTo(setStart, h);\n      context.lineTo(r, h);\n      context.bezierCurveTo(r, 0, r, 0, setStart, 0);\n      context.closePath();\n      return context;\n    }\n  };\n}","pinned":false,"mode":"js","data":null,"name":null},{"id":44,"value":"x = d3.scaleLinear(\n  [0, 60 * 60 * 24],\n  [margin.left, width - margin.right - margin.left]\n)","pinned":false,"mode":"js","data":null,"name":null},{"id":1283,"value":"md`### Formatting`","pinned":false,"mode":"js","data":null,"name":null},{"id":131,"value":"formatDate = d3.timeFormat(\"%Y-%m-%d\")","pinned":false,"mode":"js","data":null,"name":null},{"id":150,"value":"formatTime = d3.timeFormat('%H:%M')","pinned":false,"mode":"js","data":null,"name":null},{"id":906,"value":"coordsFormat = coordinates =>\n  formatcoords(coordinates[1], coordinates[0]).format({\n    latLonSeparator: ', ',\n    decimalPlaces: 2\n  })","pinned":false,"mode":"js","data":null,"name":null},{"id":1289,"value":"md`### Constants`","pinned":false,"mode":"js","data":null,"name":null},{"id":242,"value":"sunMargins = ({\n  top: 175,\n  bottom: 50\n})","pinned":false,"mode":"js","data":null,"name":null},{"id":39,"value":"margin = ({\n  top: 35,\n  bottom: 35,\n  left: 50,\n  right: 50\n})","pinned":false,"mode":"js","data":null,"name":null},{"id":26,"value":"height = 500","pinned":false,"mode":"js","data":null,"name":null},{"id":1184,"value":"colors = ({\n  YELLOW: '#f5b041',\n  DARKYELLOW: '#f39c12',\n  DARKBLUE: '#062B79',\n  LIGHTBLUE: '#5995B7'\n})","pinned":false,"mode":"js","data":null,"name":null},{"id":1304,"value":"md`### Utils`","pinned":false,"mode":"js","data":null,"name":null},{"id":651,"value":"localizeDate = d => {\n  const mDate = m(d).tz(timezoneName);\n  return calcTime(mDate.toDate(), mDate._offset);\n}","pinned":false,"mode":"js","data":null,"name":null},{"id":360,"value":"function calcTime(d, offset) {\n  var utc = d.getTime() + d.getTimezoneOffset() * 60000;\n  var nd = new Date(utc + 36000 * offset);\n  return nd;\n}","pinned":false,"mode":"js","data":null,"name":null},{"id":81,"value":"function getSecondsInDay(t) {\n  return t.getHours() * 60 * 60 + t.getMinutes() * 60 + t.getSeconds();\n}","pinned":false,"mode":"js","data":null,"name":null},{"id":853,"value":"md`### Data`","pinned":false,"mode":"js","data":null,"name":null},{"id":861,"value":"md`Get a list of all days in the current year`","pinned":false,"mode":"js","data":null,"name":null},{"id":10,"value":"days = d3.timeDays(\n  d3.timeYear(Date.now()),\n  d3.timeYear(m(Date.now()).add(1, 'year'))\n)","pinned":false,"mode":"js","data":null,"name":null},{"id":874,"value":"md`Get metadata about when the sun will rise/set for each day, using [suncalc](https://github.com/mourner/suncalc). Localize the day to the given coordinates.`","pinned":false,"mode":"js","data":null,"name":null},{"id":5,"value":"times = days\n  .map(day => ({\n    day,\n    sun: suncalc.getTimes(day, coordinates[1], coordinates[0])\n  }))\n  .map(({ day, sun }) => {\n    return {\n      ...sun,\n      day,\n      localSunrise: localizeDate(sun.sunrise),\n      localSunset: localizeDate(sun.sunset),\n      localDawn: localizeDate(sun.dawn),\n      localDusk: localizeDate(sun.dusk),\n      localSunriseEnd: localizeDate(sun.sunriseEnd),\n      localSunsetStart: localizeDate(sun.sunsetStart)\n    };\n  })","pinned":false,"mode":"js","data":null,"name":null},{"id":880,"value":"md`Now we have, for every day in ${times[\n  times.length - 1\n].solarNoon.getFullYear()}, the time the sun will rise and set for the coordinates ${JSON.stringify(\n  coordinates\n)}. `","pinned":false,"mode":"js","data":null,"name":null},{"id":286,"value":"timezoneName = tz(coordinates[1], coordinates[0])","pinned":false,"mode":"js","data":null,"name":null},{"id":960,"value":"world = FileAttachment(\"world-atlast-1-110m.json\").json()","pinned":false,"mode":"js","data":null,"name":null},{"id":888,"value":"md`---`","pinned":false,"mode":"js","data":null,"name":null},{"id":812,"value":"params = new URL(location).searchParams","pinned":false,"mode":"js","data":null,"name":null},{"id":1312,"value":"md`### 3rd Party Libs`","pinned":false,"mode":"js","data":null,"name":null},{"id":2,"value":"suncalc = require('suncalc')","pinned":false,"mode":"js","data":null,"name":null},{"id":8,"value":"d3 = require('d3@5.9')","pinned":false,"mode":"js","data":null,"name":null},{"id":282,"value":"tz = require('tz-lookup@6.1.25/tz.js').catch(() => window[\"tzlookup\"])","pinned":false,"mode":"js","data":null,"name":null},{"id":308,"value":"m = require(await FileAttachment(\"moment-timezone-0.5.27.js\").url())","pinned":false,"mode":"js","data":null,"name":null},{"id":970,"value":"topojson = require(\"topojson-client@3\")","pinned":false,"mode":"js","data":null,"name":null},{"id":1336,"value":"import { Scrubber } from \"@mbostock/scrubber\"","pinned":false,"mode":"js","data":null,"name":null},{"id":893,"value":"formatcoords = require('formatcoords@1.1.3/index.js').catch(\n  () => window[\"formatcoords\"]\n)","pinned":false,"mode":"js","data":null,"name":null},{"id":233,"value":"import { worldMapCoordinates } with {\n  world,\n  d3 as d3geo,\n  topojson\n} from \"@jashkenas/inputs\"","pinned":false,"mode":"js","data":null,"name":null}],"resolutions":[],"schedule":null,"last_view_time":null}