Ripple

1 Preface

Applied signal processing in Clojure

Ripple provides high-performance signal processing algorithms with a focus on scientific computing applications.

While Fastmath provides general scientific computing capabilities, Ripple offers a space for specialized methods of specific domains.

Current modules:

  • MALDI-TOF mass spectrometry β€” MALDIquant-compatible preprocessing pipeline (validated against the R reference implementation)
  • Cardiovascular signals β€” ECG and PPG processing: filtering, peak detection, and heart rate variability analysis
  • Respiratory signals β€” Breathing rate, amplitude, phase, symmetry, RRV, and RVT (ported from NeuroKit2)

General info

Website https://scicloj.github.io/ripple/
Source (GitHub repo)
Deps Clojars Project
License MIT
Status πŸ› alphaπŸ› 

Features

MALDI-TOF Mass Spectrometry

  • Variance stabilization β€” Square root transformation
  • Noise reduction β€” Savitzky-Golay polynomial smoothing, moving average, median filter
  • Baseline correction β€” SNIP (Statistics-sensitive Non-linear Iterative Peak-clipping), TopHat morphological filter
  • Normalization β€” TIC (Total Ion Current) using trapezoid rule, median calibration
  • Peak detection β€” Local maxima with MAD noise estimation and SNR filtering
  • Spectral binning β€” Convert variable-length spectra to fixed-width feature vectors for ML
  • Multi-sample alignment β€” Peak binning, frequency filtering, and intensity matrix construction

All algorithms validated against R MALDIquant β€” exact match or < 1e-5 difference.

Cardiovascular Signal Processing

  • Butterworth filtering β€” High-pass, band-pass, and band-stop (notch) filters via jDSP
  • ECG cleaning β€” NeuroKit2 (broadband) and Hamilton (QRS-band) methods
  • PPG cleaning β€” Elgendi bandpass method
  • R-peak detection β€” NeuroKit gradient-based and Hamilton adaptive threshold methods
  • PPG systolic peak detection β€” Elgendi two-moving-average method
  • Artifact correction β€” Missed/extra beat handling via RR-interval analysis
  • Heart rate variability β€” Time-domain indices (MeanNN, SDNN, RMSSD, pNN50, CVNN, etc.)
  • Synthetic signal generators β€” ECGSYN ECG and Gaussian-stamp PPG with configurable heart rate, noise, and drift

Respiratory Signal Processing

  • Bandpass filtering β€” Khodadad2018 method (0.05–3 Hz Butterworth)
  • Peak and trough detection β€” Prominence-based filtering for robust inhalation/exhalation onset detection
  • Breathing rate β€” Instantaneous and continuous (Akima spline interpolation)
  • Respiratory amplitude β€” Standard and prepost methods
  • Phase labeling β€” Inspiration/expiration with completion percentage
  • Cycle symmetry β€” Peak-trough ratio (Cole & Voytek, 2019)
  • Respiratory rate variability (RRV) β€” Time-domain indices (SDBB, RMSSD, CVBB, etc.)
  • Respiratory volume per time (RVT) β€” Power2020 method for fMRI confound estimation
  • Synthetic signal generator β€” Sinusoidal model with seedable RNG

Installation

Add to your deps.edn:

{:deps {org.scicloj/ripple {:mvn/version "0.1.0"}}}

Quick Start

MALDI-TOF

(require '[scicloj.ripple.maldi :as maldi]
         '[tablecloth.api :as tc])

;; A spectrum is a dataset with :mass and :intensity columns
(def spectrum (tc/dataset {:mass masses :intensity intensities}))

;; Preprocess with MALDIquant-compatible pipeline
(def preprocessed
  (maldi/preprocess-spectrum-data
   spectrum
   {:should-sqrt-transform true
    :smooth-window 11
    :baseline-iterations 20
    :should-tic-normalize true}))

;; Detect peaks
(def peaks (maldi/detect-peaks (:intensity preprocessed)
                               {:half-window-size 20 :snr 2}))

;; Bin for ML (6000 fixed-width bins, DRIAMS parameters)
(def binned (maldi/bin-spectrum preprocessed {:range [2000 20000] :step 3}))

Cardiovascular Signals

(require '[scicloj.ripple.cardio :as cardio])

;; Generate a synthetic ECG (or use real data as a double array)
(def ecg (cardio/synthetic-ecg {:sampling-rate 500 :duration 60 :heart-rate 72}))

;; Clean β†’ detect R-peaks β†’ compute HRV
(def cleaned (cardio/ecg-clean ecg 500 {:method :neurokit :powerline 50}))
(def peaks   (cardio/ecg-findpeaks cleaned 500 {:method :neurokit}))
(def rr      (cardio/peaks->rr-intervals peaks 500))
(def hrv     (cardio/hrv-time rr))

(:mean-hr hrv)  ;; => ~72.0
(:rmssd hrv)    ;; parasympathetic tone index (ms)

Respiratory Signals

(require '[scicloj.ripple.rsp :as rsp])

;; Generate a synthetic respiratory signal (or use real data as a double array)
(def signal (rsp/synthetic-rsp {:sampling-rate 1000 :duration 60 :respiratory-rate 15}))

;; Clean β†’ detect peaks/troughs β†’ compute RRV
(def cleaned  (rsp/rsp-clean signal 1000 {:method :khodadad2018}))
(def extrema  (rsp/rsp-findpeaks cleaned 1000 {}))
(def bb       (rsp/peaks->bb-intervals (:troughs extrema) 1000))
(def rrv      (rsp/rrv-time bb))

(:mean-br rrv)  ;; => ~15.0 BPM
(:sdbb rrv)     ;; breath-to-breath variability (ms)

Documentation

See the Ripple book for tutorials and API documentation.

API Namespaces

Namespace Purpose
scicloj.ripple.maldi Public MALDI API β€” preprocessing, peaks, binning, multi-sample alignment
scicloj.ripple.cardio Public cardio API β€” filters, peaks, RR, HRV
scicloj.ripple.rsp Public RSP API β€” cleaning, peaks, amplitude, phase, symmetry, rate, RRV, RVT

Development

./run_tests.sh              # run all tests (requires R + MALDIquant)
./setup_r.sh                # install MALDIquant
./setup_python.sh           # install NeuroKit2 + HeartPy (for Python interop notebook)
clojure -T:build ci         # test + build JAR

References

License

MIT License β€” see LICENSE file.


Part of the scicloj ecosystem for scientific computing in Clojure.

Chapters in this book

source: notebooks/index.clj