npm package discovery and stats viewer.

Discover Tips

  • General search

    [free text search, go nuts!]

  • Package details

    pkg:[package-name]

  • User packages

    @[username]

Sponsor

Optimize Toolset

I’ve always been into building performant and accessible sites, but lately I’ve been taking it extremely seriously. So much so that I’ve been building a tool to help me optimize and monitor the sites that I build to make sure that I’m making an attempt to offer the best experience to those who visit them. If you’re into performant, accessible and SEO friendly sites, you might like it too! You can check it out at Optimize Toolset.

About

Hi, 👋, I’m Ryan Hefner  and I built this site for me, and you! The goal of this site was to provide an easy way for me to check the stats on my npm packages, both for prioritizing issues and updates, and to give me a little kick in the pants to keep up on stuff.

As I was building it, I realized that I was actually using the tool to build the tool, and figured I might as well put this out there and hopefully others will find it to be a fast and useful way to search and browse npm packages as I have.

If you’re interested in other things I’m working on, follow me on Twitter or check out the open source projects I’ve been publishing on GitHub.

I am also working on a Twitter bot for this site to tweet the most popular, newest, random packages from npm. Please follow that account now and it will start sending out packages soon–ish.

Open Software & Tools

This site wouldn’t be possible without the immense generosity and tireless efforts from the people who make contributions to the world and share their work via open source initiatives. Thank you 🙏

© 2026 – Pkg Stats / Ryan Hefner

@granite-elements/granite-timeline

v3.0.0

Published

A timeline rendering web component using Lit and d3

Readme

Published on webcomponents.org

granite-timeline

A timeline rendering web component built with Lit and d3 v7.

v3.0.0 is a full rewrite: Lit instead of Polymer, native d3 v7 rendering instead of the abandoned d3-timelines plugin, plain ES modules, no polyfills, no runtime script loading. See Migration from v2.

Install

npm install @granite-elements/granite-timeline

Usage

import '@granite-elements/granite-timeline';
<granite-timeline
    data='[{"times":[{"starting_time":1355752800000,"ending_time":1355759900000}, {"starting_time":1355767900000,"ending_time":1355774400000}]},{"times":[{"starting_time":1355759910000,"ending_time":1355761900000}]}]'
    show-time-axis></granite-timeline>

Function- and object-valued options are set as properties:

import { scaleOrdinal } from 'd3-scale';
import { timeHour } from 'd3-time';

const el = document.querySelector('granite-timeline');
el.data = [
  { label: 'fruit 1', fruit: 'orange', times: [
    { starting_time: 1355759910000, ending_time: 1355761900000 }] },
  { label: 'fruit 2', fruit: 'apple', times: [
    { starting_time: 1355752800000, ending_time: 1355759900000 }] },
];
el.colors = scaleOrdinal().domain(['apple', 'orange']).range(['#6b0000', '#ef9b0f']);
el.colorsProperty = 'fruit';
el.tickTime = timeHour;

Data format

[
  {
    label: 'series label',     // optional, shown on the left when `stack` is set
    times: [
      {
        starting_time: 1355752800000,  // ms epoch
        ending_time: 1355759900000,    // ms epoch
        label: 'bar label',            // optional
        color: '#6b0000',              // optional, overrides the color scale
      },
    ],
  },
]

Properties

| Property | Attribute | Type | Default | Description | |---|---|---|---|---| | data | data | Array | [] | The timeline data (see above) | | width | width | Number | element width | Width of the timeline in pixels | | height | height | Number | computed | Height of the timeline in pixels | | itemHeight | item-height | Number | 20 | Height of a data series row | | itemMargin | item-margin | Number | 5 | Margin between data series rows | | marginTop | margin-top | Number | 30 | Top margin | | marginBottom | margin-bottom | Number | 30 | Bottom margin | | marginLeft | margin-left | Number | 30 | Left margin | | marginRight | margin-right | Number | 30 | Right margin | | tickFormat | tick-format | String|Function | '%I %p' | d3 time-format specifier, or a (date) => string function (property only) | | tickTime | — | d3-time interval | — | Tick time unit, e.g. timeHour from d3-time | | tickInterval | tick-interval | Number | 1 | Tick interval, used with tickTime | | numTicks | num-ticks | Number | — | Number of ticks, used when tickTime is unset | | tickSize | tick-size | Number | 6 | Tick size in pixels | | tickValues | — | Array | — | Explicit tick values (Date or ms epoch) | | rotateTicks | rotate-ticks | Number | 0 | Rotation of the tick labels in degrees | | axisTop | axis-top | Boolean | false | Places the time axis on top | | axisZoom | axis-zoom | Boolean | false | Enables zooming (Ctrl/⌘ + wheel, pinch, double-click) and panning (drag) of the time axis | | colors | — | d3 ordinal scale | scaleOrdinal(schemeCategory10) | Color scale for the series | | colorsProperty | colors-property | String | — | Data property mapped to the colors scale | | beginning | beginning | Date|Number|String | computed | Start of the timeline | | ending | ending | Date|Number|String | computed | End of the timeline | | stack | stack | Boolean | false | Stacks each data series on its own row | | showToday | show-today | Boolean | false | Shows a vertical line at the current time | | todayMarginTop | today-margin-top | Number | 25 | Top margin of the today line | | todayMarginBottom | today-margin-bottom | Number | 0 | Bottom margin of the today line | | todayWidth | today-width | Number | 2 | Stroke width of the today line | | todayColor | today-color | String | rgb(245, 157, 0) | Color of the today line | | showTimeAxis | show-time-axis | Boolean | false | Shows the time axis | | background | background | String | — | Background color of the rows | | rowSeparators | row-separators | String | — | Color of the separator lines between rows | | labelFormat | — | Function | — | Maps a raw label value to its display text | | debug | debug | Boolean | false | Logs debug information to the console |

Color resolution order for each bar: time.color → colors(time[colorsProperty]) → colors(series[colorsProperty]) → colors(seriesIndex).

Events

All events are CustomEvents dispatched from the element, with detail: { d, index, datum, mouse, evt } where d is the time entry, index its index in the series, datum the series object, mouse the [x, y] pointer position in the SVG, and evt the originating DOM event.

| Event | Fired on | |---|---| | click | Click on a timeline bar | | mouseover | Pointer enters a bar | | mouseout | Pointer leaves a bar | | hover | Pointer moves over a bar |

Note: a click listener also receives native click events from the element; check event.detail?.d to distinguish bar clicks.

When axisZoom is enabled, a zoom event is fired on every zoom/pan, with detail: { start, end, transform } where start/end are the Date bounds of the visible domain and transform the d3 zoom transform.

Methods

| Method | Description | |---|---| | resetZoom() | Resets the axis zoom/pan to the initial full-domain view |

Styling

The chart renders in shadow DOM. Customization hooks:

| Hook | Description | |---|---| | --granite-timeline-label-color | Color of the series and bar labels | | --granite-timeline-axis-color | Color of the time axis | | ::part(timeline) | The chart container |

Demo

npm install
npm run dev    # open http://localhost:5173/demo/

Migration from v2

  • No more script loading: d3 is now a regular ES-module dependency. Remove any granite-js-dependencies-grabber setup; bower and the webcomponentsjs polyfills are gone.
  • Dropped properties: displayCircles, relativeTime, showBorderLine (+ its borderLine* format properties), showTimeAxisTick (+ timeAxisTick*), xAxisClass. Open an issue if you need one of them back.
  • axisZoom is kept, but zooming with the mouse wheel now requires Ctrl/⌘ so the chart doesn't hijack page scrolling; drag pans, and a zoom event reports the visible domain.
  • Dropped events: scroll. The i field of event details is gone — use index.
  • Tick intervals: tickTime now takes a modern d3-time interval (import { timeHour } from 'd3-time') instead of the old d3.time.hours.
  • tickFormat is now a single value (string specifier or function) instead of the v2 object — the other tick options moved to top-level properties (unchanged names).
  • Default palette changed from d3.scale.category20() (removed in d3 v7) to scaleOrdinal(schemeCategory10).
  • Shadow DOM styling: page CSS no longer reaches the chart internals. Use the CSS custom properties / part listed above.

License

MIT License