| Title: | Sleep and Circadian Metrics Estimation from Actigraphy Data |
|---|---|
| Description: | A generic sleep–wake cycle detection algorithm for analyzing unlabeled actigraphy data. The algorithm has been validated against event markers using data from the Multi-Ethnic Study of Atherosclerosis (MESA) Sleep study, and its methodological details are described in Chen and Sun (2024) <doi:10.1098/rsos.231468>. The package provides functions to estimate sleep metrics (e.g., sleep and wake onset times) and circadian rhythm metrics (e.g., mesor, phasor, interdaily stability, intradaily variability), as well as tools for screening actigraphy quality, fitting cosinor models, and performing parametric change point detection. The workflow can also be used to segment long actigraphy sequences into regularized structures for physical activity research. |
| Authors: | Shanshan Chen [aut, cre], Jonathon Jacobs [ctb] |
| Maintainer: | Shanshan Chen <[email protected]> |
| License: | GPL (>= 3) |
| Version: | 0.1.2 |
| Built: | 2026-05-12 07:34:37 UTC |
| Source: | https://github.com/cran/CircaCP |
A single-subject actigraphy dataset from the NHANES 2013–2014 study, provided as an example for demonstrating the CircaCP workflow.
actigraphyactigraphy
A data frame with one row per recorded epoch and the following variables:
Date of recording (synthetic or reconstructed from NHANES information).
Time of day corresponding to each observation.
Light intensity.
Short-term variability of light intensity.
Activity magnitude calculated using the MIMS algorithm.
Raw or calibrated X-axis signal from the accelerometer.
Raw or calibrated Y-axis signal from the accelerometer.
Raw or calibrated Z-axis signal from the accelerometer.
National Health and Nutrition Examination Survey (NHANES) 2013–2014.
data(actigraphy) head(actigraphy)data(actigraphy) head(actigraphy)
Detect a single change point (parametric methods)
cp_detect(M, dist)cp_detect(M, dist)
M |
minute-level Activity vector; |
dist |
Actigraphy data distribution family,
including |
the location of the single change point
Computes five nonparametric metrics from minute-level activity: Relative Amplitude (RA), Interdaily Stability (IS), Intradaily Variability (IV), the least-active 5-hour block (L5), and the most-active 10-hour block (M10).
extract_nonparametric_metrics(df, L_window = 5 * 60, M_window = 10 * 60)extract_nonparametric_metrics(df, L_window = 5 * 60, M_window = 10 * 60)
df |
cleaned data frame containing the activity varialbe at 1-minute epoch |
L_window |
Integer window length (minutes) for L5 (default 300). |
M_window |
Integer window length (minutes) for M10 (default 600). |
A list with components:
Relative amplitude, when denominator .
Interdaily stability (0..1).
Intradaily variability ().
Mean activity in the lowest 5-hour block of the 24 h profile.
Minute-of-day (0~1439) at which L5 starts.
Mean activity in the highest 10-hour block of the 24 h profile.
Minute-of-day (0~1439) at which M10 starts.
Length-1440 vector of minute-of-day means.
screen_wear(), sleep_detection(), extract_sleep_metrics
From minute-level data with sleep/wake labels (label.sw 1 = sleep, 0 = wake),
extracts sleep/wake onsets, episode durations, circular SDs of onset times,
Sleep Regularity Index (SRI), cosinor parameters, day/night variance ratio,
and nonparametric metrics (RA, IS, IV, L5, M10). Returns one row per episode
with scalar metrics repeated per row (tidy format).
extract_sleep_metrics(df, min_sleep_episode_min = 180L)extract_sleep_metrics(df, min_sleep_episode_min = 180L)
df |
|
min_sleep_episode_min |
Minimum duration (minutes) to treat as a main sleep episode. |
A data.frame with columns including:
Subject ID obtained from the stem of filename.
sleep or wake
datetime of sleep onset time and wake onset time
timestamps presented as minutes of the day since midnight
sleep duration or wake duration
Standard devation of sleep onset time (calculated by circular statistics)
Standard devation of sleep onset time (calculated by circular statistics)
Sleep regularity index
parameters obtained from the cosinor model
nonparametrics actigraphy metrics
sleep_detection(), sleep_cos(), extract_nonparametric_metrics()
Splits a minute-level, labeled time series into contiguous episodes of a
target state (sleep or wake) and returns the activity vectors for those
episodes whose length is at least min_len minutes.
extract_sw_period(labeled_df, target_state = 1, min_len = 30)extract_sw_period(labeled_df, target_state = 1, min_len = 30)
labeled_df |
A
|
target_state |
Integer |
min_len |
Integer minimum episode length in minutes (i.e., number of
consecutive samples) required to keep an episode. Default is |
The function uses run-length encoding over label.sw to identify contiguous
episodes. Any NA in label.sw is converted to a sentinel and treated as a
hard break (i.e., episodes do not cross NA gaps). Length filtering is
applied on the number of minutes (rows) per episode.
A list of numeric vectors. Each element is the Activity values
for one qualifying episode of the requested state. If no episode qualifies,
returns an empty list (list()).
#' @export
Activity
Reads a CSV/TSV, automatically strips any leading header lines, selects user
specified Date and Time columns, and harmonizes one chosen activity
column to the canonical name Activity. Adds an id (defaults to the file
stem if not supplied).
import_acti_file( file, date_col, time_col, activity_cols, id = NULL, keep_extra = FALSE, drop_original_activity_cols = TRUE )import_acti_file( file, date_col, time_col, activity_cols, id = NULL, keep_extra = FALSE, drop_original_activity_cols = TRUE )
file |
Character path to the actigraphy file. |
date_col, time_col
|
Character names of the date and time columns in |
activity_cols |
Character vector of candidate activity columns; the first
that exists will be used and renamed to |
id |
Optional subject id (character). Defaults to the filename stem. |
keep_extra |
Logical; if |
drop_original_activity_cols |
Logical; if TRUE, drop the original activity |
Internally uses data.table::fread() with automatic header detection
(skips lines before the first row that looks like a header). No time zone
conversion is performed.
A data.frame with at least columns id, Date, Time, Activity.
Determines the native epoch from the first two time stamps, decimates to
1-minute resolution (if needed), checks total minutes 1440*min_days,
and within that finds the longest contiguous segment where runs of
consecutive zeros do not exceed max_zero_run minutes.
screen_wear( df, min_days = 5L, max_zero_run = 120L, date_col = "Date", time_col = "Time", activity_col = "Activity" )screen_wear( df, min_days = 5L, max_zero_run = 120L, date_col = "Date", time_col = "Time", activity_col = "Activity" )
df |
|
min_days |
Integer minimum number of whole days required (default 5). |
max_zero_run |
Integer maximum allowed length (minutes) of a run of zeros. |
date_col |
Name of the date column. |
time_col |
Name of the time column. |
activity_col |
Name of the activity column used to determine wear/non-wear. |
Decimation rule: 15 s factor 4; 30 s factor 2;
60 s factor 1. The zero-run criterion is applied on the
1-minute Activity series.
A list with elements:
"ok" if a qualifying segment is found, otherwise a message.
Detected original epoch in seconds (15, 30, 60).
Indices of the kept segment in the input.
Minute-level data.frame of the selected segment (if ok).
import_acti_file(), sleep_cos(), sleep_detection()
Fits with period minutes
to a rescaled activity series. Returns fitted curve, binary curve after
thresholding, and canonicalized parameters (non-negative amplitude).
MESOR (mesor)
The baseline or “midline” level around which the rhythm oscillates.
Units = same as actigraphy your data
Roughly the average activity across the cycle.
sleep_cos(clean_df, thr = 0.2)sleep_cos(clean_df, thr = 0.2)
clean_df |
cleaned dataframe with cleaned_df$Activity. |
thr |
Dichotomization threshold for fitted curve. |
Amplitude (amp) Half the peak-to-trough swing of the fitted rhythm. Units is the same as actigraphy data. Larger amplitude → stronger rhythmicity (bigger day–night contrast). Negative amp will be flipped, and P/2 will be added to phase. Acrophase (phase) The timing of the peak of the fitted cosine. Units is the epoch units of the data (e.g. minutes). P=1440, interpret phase as minutes-of-day relative to your x origin.
A list with elements:
fitted cosine curve.
dichotimized cosine curve
c(Mesor, Amplitude, Acrophase).
Root mean squared error between fitted cosine curve and data.
screen_wear(), sleep_detection(), extract_sleep_metrics()
It first uses a 24 h cosinor fit (via sleep_cos()) and a chosen thresholding rule to
label each minute as sleep (label.sw = 1) or wake (label.sw = 0).
Reference: Shanshan Chen, and Xinxin Sun.Validating CircaCP:
a generic sleep–wake cycle detection algorithm for unlabelled actigraphy data.
Royal Society Open Science 11, no. 5 (2024): 231468.
sleep_detection(clean_df, thr = 0.2, dist = "ZAG")sleep_detection(clean_df, thr = 0.2, dist = "ZAG")
clean_df |
Minute-level |
thr |
Numeric threshold in [0, 1] applied to a rescaled cosinor fit. |
dist |
Character method key (e.g., |
a data.frame augmenting the input df including the following additional variables:
fitted cosine curve
circadian cycle estimated by dichotimized cosine curve
sleep-wake cycle estimated by CircaCP
range-normalized activity levels
screen_wear(), sleep_cos(),cp_detect(), extract_sleep_metrics()