diff --git a/NEWS.md b/NEWS.md index 630c5beb5..3fd9de28d 100644 --- a/NEWS.md +++ b/NEWS.md @@ -9,6 +9,9 @@ - Part 5: Fix bug in addition of first wake-up time if not present #1179 - Part 2: Correctly skip MXLX calculation when it cannot be calculated, which caused error when trying to use the output. Fixes #1180 + +- Part 1: Add parameter nonwear_range_threshold to control range threshold for nonwear detection, +this used to be a constant. And default changed to 50mg. #1172 # CHANGES IN GGIR VERSION 3.1-2 diff --git a/R/check_params.R b/R/check_params.R index f1f7f19eb..7bda68d0a 100644 --- a/R/check_params.R +++ b/R/check_params.R @@ -59,7 +59,8 @@ check_params = function(params_sleep = c(), params_metrics = c(), "rmc.col.acc", "interpolationType", "rmc.firstrow.acc", "rmc.firstrow.header", "rmc.header.length", "rmc.col.temp", "rmc.col.time", - "rmc.sf", "rmc.col.wear", "rmc.noise", "frequency_tol", "rmc.scalefactor.acc") + "rmc.sf", "rmc.col.wear", "rmc.noise", "frequency_tol", + "rmc.scalefactor.acc", "nonwear_range_threshold") boolean_params = c("printsummary", "do.cal", "rmc.unsignedbit", "rmc.check4timegaps", "rmc.doresample", "imputeTimegaps") character_params = c("backup.cal.coef", "rmc.dec", "rmc.unit.acc", diff --git a/R/g.getmeta.R b/R/g.getmeta.R index 96937ed04..2a61b3ef5 100644 --- a/R/g.getmeta.R +++ b/R/g.getmeta.R @@ -126,13 +126,10 @@ g.getmeta = function(datafile, params_metrics = c(), params_rawdata = c(), deviceSerialNumber = hvars$deviceSerialNumber # get now-wear, clip, and blocksize parameters (thresholds) - ncb_params = get_nw_clip_block_params(chunksize = params_rawdata[["chunksize"]], - dynrange = params_rawdata[["dynrange"]], - monc = mon, dformat = dformat, + ncb_params = get_nw_clip_block_params(monc = mon, dformat = dformat, deviceSerialNumber = deviceSerialNumber, - rmc.noise = params_rawdata[["rmc.noise"]], sf = sf, - rmc.dynamic_range = params_rawdata[["rmc.dynamic_range"]]) + params_rawdata = params_rawdata) clipthres = ncb_params$clipthres blocksize = ncb_params$blocksize sdcriter = ncb_params$sdcriter diff --git a/R/get_nw_clip_block_params.R b/R/get_nw_clip_block_params.R index 802df6eb7..a3341400c 100644 --- a/R/get_nw_clip_block_params.R +++ b/R/get_nw_clip_block_params.R @@ -1,14 +1,14 @@ -get_nw_clip_block_params = function(chunksize, dynrange, monc, dformat, deviceSerialNumber = "", rmc.noise=c(), sf, - rmc.dynamic_range) { - blocksize = round(14512 * (sf/50) * chunksize) - if (monc == MONITOR$GENEA) blocksize = round(21467 * (sf/80) * chunksize) +get_nw_clip_block_params = function(monc, dformat, deviceSerialNumber = "", sf, + params_rawdata) { + blocksize = round(14512 * (sf/50) * params_rawdata[["chunksize"]]) + if (monc == MONITOR$GENEA) blocksize = round(21467 * (sf/80) * params_rawdata[["chunksize"]]) if (monc == MONITOR$ACTIGRAPH && dformat == FORMAT$CSV) blocksize = round(blocksize)#round(blocksize/5) - if (monc == MONITOR$ACTIGRAPH && dformat == FORMAT$GT3X) blocksize = (24 * 3600) * chunksize + if (monc == MONITOR$ACTIGRAPH && dformat == FORMAT$GT3X) blocksize = (24 * 3600) * params_rawdata[["chunksize"]] if (monc == MONITOR$AXIVITY && dformat == FORMAT$CWA) { if (utils::packageVersion("GGIRread") >= "0.3.1") { # 24-hour block. # CWA data blocks can have 40, 80 or 120 samples each; we'll take 80 as the average number. - blocksize = round(24 * 3600 * sf / 80 * chunksize) + blocksize = round(24 * 3600 * sf / 80 * params_rawdata[["chunksize"]]) } else { blocksize = round(blocksize * 1.0043) } @@ -17,7 +17,7 @@ get_nw_clip_block_params = function(chunksize, dynrange, monc, dformat, deviceSe if (monc == MONITOR$MOVISENS) blocksize = sf * 60 * 1440 if (monc == MONITOR$VERISENSE && dformat == FORMAT$CSV) blocksize = round(blocksize) - + dynrange = params_rawdata[["dynrange"]] if (monc == MONITOR$ACTIGRAPH) { # If Actigraph then try to specify dynamic range based on Actigraph model if (length(grep(pattern = "CLE", x = deviceSerialNumber)) == 1) { @@ -38,20 +38,20 @@ get_nw_clip_block_params = function(chunksize, dynrange, monc, dformat, deviceSe if (monc == MONITOR$MOVISENS) { clipthres = 15.5 # hard coded assumption that dynamic range is 16g } else if (monc == MONITOR$AD_HOC) { - clipthres = rmc.dynamic_range + clipthres = params_rawdata[["rmc.dynamic_range"]] } } # Nonwear threshold: non-wear criteria are monitor-specific - racriter = 0.15 # very likely irrelevant parameters, but leave in for consistency + racriter = params_rawdata[["nonwear_range_threshold"]] / 1000 sdcriter = 0.013 #if (monc == MONITOR$GENEA) { sdcriter = 0.003; racriter = 0.05 } if (monc == MONITOR$VERISENSE) { racriter = 0.20 } else if (monc == MONITOR$AD_HOC) { - if (length(rmc.noise) == 0) { + if (length(params_rawdata[["rmc.noise"]]) == 0) { stop("Argument rmc.noise not specified, please specify expected noise level in g-units") } - sdcriter = rmc.noise * 1.2 + sdcriter = params_rawdata[["rmc.noise"]] * 1.2 } invisible(list(clipthres=clipthres, blocksize=blocksize, sdcriter=sdcriter, racriter=racriter)) } diff --git a/R/load_params.R b/R/load_params.R index 04638d848..cd650a344 100644 --- a/R/load_params.R +++ b/R/load_params.R @@ -61,7 +61,7 @@ load_params = function(topic = c("sleep", "metrics", "rawdata", rmc.desiredtz = NULL, rmc.configtz = NULL, rmc.sf = c(), rmc.headername.sf = c(), rmc.headername.sn = c(), rmc.headername.recordingid = c(), rmc.header.structure = c(), - rmc.check4timegaps = FALSE, rmc.noise = 13, + rmc.check4timegaps = FALSE, rmc.noise = 13, nonwear_range_threshold = 50, rmc.col.wear = c(), rmc.doresample = FALSE, interpolationType = 1, imputeTimegaps = TRUE, frequency_tol = 0.1, rmc.scalefactor.acc = 1) diff --git a/man/GGIR.Rd b/man/GGIR.Rd index fd7c439ac..60048c3dd 100755 --- a/man/GGIR.Rd +++ b/man/GGIR.Rd @@ -513,7 +513,8 @@ GGIR(mode = 1:5, \item{rmc.noise}{ Numeric (default = 13). - Noise level of acceleration signal in m\emph{g}-units, used when working ad-hoc .csv data formats + Noise level of acceleration signal in m\emph{g}-units, used when working + ad-hoc .csv data formats using \link{read.myacc.csv}. The \link{read.myacc.csv} does not take rmc.noise as argument, but when interacting with \link{GGIR} or \link{g.part1} rmc.noise is used.} @@ -530,6 +531,11 @@ GGIR(mode = 1:5, by lack of movement with gravitational oriationed guessed from most recent valid data block. Only applicable to Axivity .cwa data. } + \item{nonwear_range_threshold}{ + Numeric (default 150) used to define maximum value range per axis for non-wear + detection, used in combination with brand specific standard deviation per + axis. + } } } diff --git a/man/get_nw_clip_block_params.Rd b/man/get_nw_clip_block_params.Rd index bf8046ea6..87faada42 100644 --- a/man/get_nw_clip_block_params.Rd +++ b/man/get_nw_clip_block_params.Rd @@ -9,16 +9,10 @@ Not designed for direct use by user. } \usage{ - get_nw_clip_block_params(chunksize, dynrange, monc, dformat, deviceSerialNumber, - rmc.noise=c(), sf, rmc.dynamic_range) + get_nw_clip_block_params(monc, dformat, deviceSerialNumber = "", sf, + params_rawdata) } \arguments{ - \item{chunksize}{ - See \link{g.calibrate} - } - \item{dynrange}{ - See \link{g.getmeta} - } \item{monc}{ See \link{g.inspectfile} } @@ -28,17 +22,11 @@ \item{deviceSerialNumber}{ As produced by \link{g.extractheadervars} } - \item{rmc.noise}{ - Noise level of acceleration signal in _g_-units, used when working ad-hoc .csv data formats - using \link{read.myacc.csv}. The \link{read.myacc.csv} does not take rmc.noise as argument, - but when interacting with \link{GGIR} or \link{g.part1} rmc.noise is used. - There, rmc.noise is taken from the params_rawdata object if not explicitly specified by user. - } - \item{sf}{ + \item{sf}{ Numeric, sample frequency in Hertz } - \item{rmc.dynamic_range}{ - Optional, please see \link{read.myacc.csv} + \item{params_rawdata}{ + See \link{GGIR} } } \keyword{internal} diff --git a/tests/testthat/test_load_check_params.R b/tests/testthat/test_load_check_params.R index fac0d3c04..35a56b84d 100644 --- a/tests/testthat/test_load_check_params.R +++ b/tests/testthat/test_load_check_params.R @@ -13,7 +13,7 @@ test_that("load_params can load parameters", { expect_equal(length(params), 8) expect_equal(length(params$params_sleep), 22) expect_equal(length(params$params_metrics), 41) - expect_equal(length(params$params_rawdata), 38) + expect_equal(length(params$params_rawdata), 39) expect_equal(length(params$params_247), 22) expect_equal(length(params$params_cleaning), 24) expect_equal(length(params$params_phyact), 14)