calculateBaseLine method

List<int?> calculateBaseLine(
  1. List<int?> millisecondsEpoch
)

Implementation

List<int?> calculateBaseLine(List<int?> millisecondsEpoch) {
  int size = millisecondsEpoch.length;
  List<int?> baselineArray = List.filled(size, null, growable: false);

  int buckets = 1001, modeIndex = 0;
  List<int?> freq = List.filled(buckets, null, growable: false);
  int? modeValue = 0,
      sumOfValues = 0,
      selectedPeak = 0; // 60-220 bpm = 1000-272 ms

  /** calculate frequency distribution of intervals**/
  for (int i = 0; i < buckets; i++) {
    freq[i] = 0;
  }

  for (int j = 0; j < millisecondsEpoch.length; j++) {
    int? epoch = millisecondsEpoch[j];
    if (epoch == 0 || epoch! >= buckets) {
      freq[0] = freq[0]! + 1;
      continue;
    }
    freq[epoch] = freq[epoch]! + 1;
  }

  /** calculate peak frequency or mode **/
  for (int i = 1; i < buckets - 1; i++) {
    if (freq[i]! > modeValue!) {
      modeValue = freq[i];
      modeIndex = i;
    }
  }

  int peak = 0;
  /** calculate limiting parameter **/
  for (int i = buckets - 1; i >= 5; i--) {
    if (sumOfValues! > (0.125 * (size - freq[0]!))) {
      if (freq[i]! >= freq[i - 5]! &&
          freq[i]! >= freq[i - 4]! &&
          freq[i]! >= freq[i - 3]! &&
          freq[i]! >= freq[i - 2]! &&
          freq[i]! >= freq[i - 1]!) {
        if (freq[i]! > 0.005 * (size - freq[0]!) ||
            (modeIndex - i).abs() <= 30) {
          selectedPeak = i;
          peak = i;
          break;
        }
      }
    }
    sumOfValues += freq[i]!;
  }

  /*if the peak is selected; other- wise, the mode is used*/
  if (selectedPeak == 0) selectedPeak = modeIndex;

  /** apply band filter with the use of limiting value
   *  low-pass filter are then set to 60 milliseconds below and above the selected peak or mode
   * **/
  baselineArray[0] = millisecondsEpoch[0];
  for (int i = 0; i < size - 1; i++) {
    // change i from 1 to 0
    if (millisecondsEpoch[i] == 0) {
      baselineArray[i] =
      millisecondsEpoch[i]; //avgLastMin(baselineFHRDR, i - 1);;
    } else {
      if (millisecondsEpoch[i]! >= (selectedPeak! + 100)) {
        baselineArray[i] =
        (selectedPeak + 100); // 60 is given in the literature
      }

      if (millisecondsEpoch[i]! <= (selectedPeak - 100)) {
        baselineArray[i] = (selectedPeak - 100);
      } else {
        baselineArray[i] = millisecondsEpoch[i];
      }
    }
    //if (Double.isNaN(_baselineArray[i]))
    //_baselineArray[i] = _baselineArray[i - 1];
  }
  //_baselineArray[0] = _millisecondsEpoch[0];
  for (int i = 1; i < size - 1; i++) {
    if (baselineArray[i] == 0) {
      baselineArray[i] =
      baselineArray[i - 1]; //avgLastMin(baselineFHRDR, i - 1);;
    } else {
      if (baselineArray[i]! >= (selectedPeak! - 50) &&
          baselineArray[i]! <=
              (selectedPeak + 50)) {
        // 60 is given in the literature
        baselineArray[i] = baselineArray[i];
      } else {
        baselineArray[i] = baselineArray[i -
            1]; //avgLastMin(baselineFHRDR, i - 1); //interpolate over previous values
      }
    }
    //if (Double.isNaN(_baselineArray[i]))
    //_baselineArray[i] = _baselineArray[i - 1];
  }
  baselineArray[size - 1] =
  baselineArray[size - 2]; //avgLastMin(baselineFHRDR, size - 2);

  double aTiny = 0.75;
  for (int i = 0; i < baselineArray.length - 1; i++) {
    baselineArray[i + 1] =
        (aTiny * baselineArray[i + 1]! + (1.0 - aTiny) * selectedPeak!)
            .toInt();
  }

  int window = 2;
  for (int i = window; i < baselineArray.length - window - 1; i++) {
    baselineArray[i] =
        getBaselineWindowSmoothAverage(baselineArray, i, window);
  }

  int avgHR;

  avgHR = calculateAvgHeartRate(baselineArray);

  // smoothing last min
  double tiny = 0.3;
  int start = baselineArray.length - window * 2;
  for (int i = 0; i < baselineArray.length - 1; i++) {
    baselineArray[i + 1] =
        (tiny * avgHR + (1.0 - tiny) * baselineArray[i + 1]!).truncate();
  }

  start = 0;
  for (int i = start; i < (window * 2) - 1; i++) {
    baselineArray[i] =
        (tiny * avgHR + (1.0 - tiny) * baselineArray[i + 1]!).truncate();
  }

  //int index = 1 * NO_OF_SAMPLES_PER_MINUTE;
  //window = index;

  avgHR = calculateLowVariationAvg(baselineArray, avgHR);

  /*avgHR = calculateLowVariationAvg(_baselineArray,avgHR);
      Log.i("avgHR",avgHR+"");
      if(avgHR <=300 || avgHR > 700)
          avgHR = calculateBasalHeartRate(_baselineArray);
      Log.i("avgHR",avgHR+"");*/

  tiny = 0.25;
  for (int i = start; i < baselineArray.length - 1; i++) {
    baselineArray[i] =
        (tiny * avgHR + (1.0 - tiny) * baselineArray[i + 1]!).truncate();
  }

  return baselineArray;
}