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

spectraview

v1.8.5

Published

Interactive React component for vibrational spectroscopy (IR, Raman, NIR)

Readme

SpectraView

Interactive React component for vibrational spectroscopy (IR, Raman, NIR).

npm version npm downloads bundle size license CI coverage Storybook

Features

  • High-performance rendering — Canvas 2D with LTTB downsampling (10K+ points at 60fps), SVG for axes and annotations
  • Zoom and pan — Mouse wheel zoom, click-drag pan, double-click reset, keyboard shortcuts (+/−/Esc)
  • Reversed x-axis — Standard IR wavenumber convention (high → low)
  • Peak detection — Automatic peak picking with prominence filtering
  • Snap crosshair — Hover readout that snaps to nearest data point with spectrum color indicator
  • Region selection — Shift+drag to select wavenumber regions interactively
  • Annotations — Positioned text labels with anchor lines on the chart
  • Multi-format parsing — JCAMP-DX, CSV/TSV, JSON, and SPC (Thermo/Galactic binary)
  • Multi-spectrum overlay — Compare spectra with automatic color assignment and legend
  • Stacked display — View multiple spectra in vertically separated panels
  • Spectral processing — Baseline correction (rubber-band), normalization (min-max, area, SNV), Savitzky-Golay smoothing, 1st/2nd derivatives
  • Spectrum comparison — Difference, addition, scaling, Pearson correlation, residuals, grid interpolation
  • Export — PNG, SVG, CSV, JSON with range filtering and precision control
  • Data table — Sortable tabular view of spectrum values with region highlighting
  • Minimap — Overview navigator showing viewport position within full spectrum
  • Tooltip — Multi-spectrum hover tooltip with nearest peak indicator
  • Undo/redo — Generic history hook for state management
  • Drag-and-drop — Built-in drop zone for loading spectrum files
  • Responsive — Optional auto-sizing to fill container width
  • Accessible — ARIA labels, keyboard navigation, screen reader support
  • Themes — Light and dark mode
  • TypeScript — Full type definitions included
  • Tiny bundle — ~48KB ESM / ~51KB CJS (no Plotly dependency)

Installation

npm install spectraview

Quick Start

import { SpectraView } from "spectraview";

const spectrum = {
  id: "1",
  label: "Sample IR",
  x: new Float64Array([4000, 3500, 3000, 2500, 2000, 1500, 1000, 500]),
  y: new Float64Array([0.1, 0.3, 0.8, 0.2, 0.5, 0.9, 0.4, 0.1]),
  xUnit: "cm⁻¹",
  yUnit: "Absorbance",
};

function App() {
  return <SpectraView spectra={[spectrum]} reverseX />;
}

Loading Files

SpectraView supports drag-and-drop file loading out of the box:

import { SpectraView, useSpectrumData } from "spectraview";

function App() {
  const { spectra, loadFile } = useSpectrumData();

  return (
    <SpectraView
      spectra={spectra}
      reverseX
      enableDragDrop
      onFileDrop={(files) => files.forEach(loadFile)}
    />
  );
}

Or parse files manually:

import { parseJcamp, parseCsv, parseJson, parseSpc } from "spectraview";

const spectra = await parseJcamp(jcampText);   // JCAMP-DX (.dx, .jdx)
const spectrum = parseCsv(csvText);             // CSV/TSV
const spectra = parseJson(jsonText);            // JSON
const spectra = parseSpc(arrayBuffer);           // SPC binary (.spc)

Peak Detection

import { SpectraView, usePeakPicking } from "spectraview";

function App() {
  const spectra = [/* your spectra */];
  const peaks = usePeakPicking(spectra, {
    prominence: 0.05,
    minDistance: 10,
    maxPeaks: 20,
  });

  return (
    <SpectraView
      spectra={spectra}
      peaks={peaks}
      onPeakClick={(peak) => console.log("Clicked:", peak.x)}
      reverseX
    />
  );
}

Spectral Processing

Apply common preprocessing transformations:

import {
  baselineRubberBand,
  normalizeMinMax,
  normalizeArea,
  normalizeSNV,
  smoothSavitzkyGolay,
  derivative1st,
  derivative2nd,
} from "spectraview";

const corrected = baselineRubberBand(spectrum.y);    // Rubber-band baseline correction
const normed = normalizeMinMax(spectrum.y);           // Scale to [0, 1]
const areaNormed = normalizeArea(spectrum.x, spectrum.y); // Unit area normalization
const snv = normalizeSNV(spectrum.y);                 // Standard Normal Variate
const smoothed = smoothSavitzkyGolay(spectrum.y, 7);  // SG smoothing (window=7)
const dy = derivative1st(spectrum.x, spectrum.y);     // 1st derivative
const d2y = derivative2nd(spectrum.x, spectrum.y);    // 2nd derivative

Or use the useNormalization hook for reactive transformations:

import { useNormalization, SpectraView } from "spectraview";

function App() {
  const [mode, setMode] = useState("none");
  const { spectra: processed, modeLabel } = useNormalization({
    spectra: rawSpectra,
    mode, // "none" | "min-max" | "area" | "snv" | "baseline" | "smooth" | "derivative"
  });

  return <SpectraView spectra={processed} reverseX />;
}

Spectrum Comparison

import {
  differenceSpectrum,
  addSpectra,
  scaleSpectrum,
  correlationCoefficient,
  residualSpectrum,
  interpolateToGrid,
} from "spectraview";

const diff = differenceSpectrum(spectrumA, spectrumB);  // A - B
const sum = addSpectra(spectrumA, spectrumB);            // A + B
const scaled = scaleSpectrum(spectrum, 2.5);             // Scale Y by factor
const r = correlationCoefficient(spectrumA, spectrumB);  // Pearson r ∈ [-1, 1]
const resid = residualSpectrum(spectrumA, spectrumB);    // |A - B|

// Align spectra to a common X grid before comparison
const aligned = interpolateToGrid(spectrumB, spectrumA.x);

Data Export

import {
  spectrumToCsv,
  multiSpectraToCsv,
  spectrumToJson,
  downloadString,
  generateSvg,
  downloadSvg,
} from "spectraview";

// CSV export with options
const csv = spectrumToCsv(spectrum, {
  delimiter: ",",
  precision: 4,
  xRange: [1000, 2000],
  includeHeader: true,
});

// Multi-spectrum CSV (shared X column)
const multiCsv = multiSpectraToCsv([spectrumA, spectrumB]);

// JSON export
const json = spectrumToJson(spectrum, { xRange: [1000, 2000] });

// Trigger browser download
downloadString(csv, "spectrum.csv", "text/csv");

API Reference

<SpectraView />

| Prop | Type | Default | Description | |------|------|---------|-------------| | spectra | Spectrum[] | required | Array of spectra to display | | width | number | 800 | Width in pixels | | height | number | 400 | Height in pixels | | reverseX | boolean | false | Reverse x-axis (IR convention) | | showGrid | boolean | true | Show grid lines | | showCrosshair | boolean | true | Show hover crosshair | | showToolbar | boolean | true | Show zoom controls | | showLegend | boolean | true | Show spectrum legend | | legendPosition | "top" \| "bottom" | "bottom" | Legend placement | | displayMode | "overlay" \| "stacked" | "overlay" | Multi-spectrum display mode | | responsive | boolean | false | Auto-size to container width | | theme | "light" \| "dark" | "light" | Color theme | | peaks | Peak[] | [] | Peak markers to display | | regions | Region[] | [] | Highlighted regions | | annotations | Annotation[] | [] | Text annotations on the chart | | snapCrosshair | boolean | true | Snap crosshair to nearest data point | | xLabel | string | auto | X-axis label override | | yLabel | string | auto | Y-axis label override | | margin | Partial<Margin> | — | Custom chart margins | | enableDragDrop | boolean | false | Enable drag-and-drop file loading | | enableRegionSelect | boolean | false | Enable Shift+drag region selection | | className | string | — | Custom CSS class | | canvasRef | RefObject<HTMLCanvasElement> | — | Ref to canvas element (for export) | | onPeakClick | (peak: Peak) => void | — | Peak click callback | | onViewChange | (view: ViewState) => void | — | Zoom/pan change callback | | onCrosshairMove | (x: number, y: number) => void | — | Crosshair move callback | | onToggleVisibility | (id: string) => void | — | Legend visibility toggle callback | | onFileDrop | (files: File[]) => void | — | File drop callback | | onRegionSelect | (region: Region) => void | — | Region selection callback |

Sub-Components

For advanced composition, individual layers are exported:

import {
  SpectrumCanvas,
  AxisLayer,
  PeakMarkers,
  RegionSelector,
  Crosshair,
  Toolbar,
  Legend,
  DropZone,
  AnnotationLayer,
  Minimap,
  Tooltip,
  DataTable,
  StackedView,
  ExportMenu,
} from "spectraview";

Hooks

| Hook | Description | |------|-------------| | useSpectrumData() | File loading and spectrum state management | | useZoomPan(options) | Zoom/pan behavior backed by d3-zoom | | usePeakPicking(spectra, options) | Automatic peak detection | | useExport() | PNG, CSV, JSON export functions | | useRegionSelect(options) | Interactive Shift+drag region selection | | useResizeObserver() | Container resize observation for responsive sizing | | useKeyboardNavigation(options) | Keyboard shortcuts (+/−/Esc for zoom/reset) | | useNormalization(options) | Reactive spectral normalization/processing | | useHistory(options) | Generic undo/redo with configurable depth |

Keyboard Shortcuts

| Key | Action | |-----|--------| | + or = | Zoom in | | - | Zoom out | | Escape | Reset zoom |

Companion: SpectraKit (Python)

SpectraView pairs with SpectraKit, a Python library for spectral data processing:

  • SpectraKit — Process spectra: baseline correction, normalization, despiking, similarity
  • SpectraView — View spectra: interactive visualization in the browser
pip install pyspectrakit  # Process in Python
npm install spectraview   # View in the browser

Browser Support

Chrome, Firefox, Safari, Edge (last 2 versions).

Contributing

See CONTRIBUTING.md.

License

MIT — Tubhyam Karthikeyan