Advertisement
Guest User

g

a guest
Apr 8th, 2025
15
0
Never
Not a member of Pastebin yet? Sign Up, it unlocks many cool features!
text 3.11 KB | None | 0 0
  1. import Toybox.Lang;
  2. import Toybox.WatchUi;
  3. import Toybox.Activity;
  4. import Toybox.Graphics;
  5.  
  6. // implements a rolling average for numerical values
  7. class RollingAverage {
  8. // options for calculating rolling average
  9. const RESET_ROLLING_AVERAGE_ON_NULL_VALUE = true;
  10. const RETURN_NULL_WHEN_ROLLING_AVERAGE_HAS_INCOMPLETE_DATA = true;
  11.  
  12. // circular "queue" for rolling average data
  13. private var _data as Array<Numeric?>;
  14. private var _startIndex as Number = 0; // current start index of the queue
  15. private var _maxSize as Number; // max size of queue
  16. private var _currentSize as Number = 0; // current size of queue
  17.  
  18. function initialize(windowSize as Number) {
  19. _maxSize = windowSize;
  20. _data = new Array<Numeric>[_maxSize];
  21. }
  22.  
  23. public function reset() {
  24. _currentSize = 0;
  25. _startIndex = 0;
  26. }
  27.  
  28. public function addValue(value as Numeric?) {
  29. if (value == null) {
  30. if (RESET_ROLLING_AVERAGE_ON_NULL_VALUE) {
  31. reset();
  32. }
  33. return;
  34. }
  35. var currentIndex = (_startIndex + _currentSize) % _maxSize;
  36. _data[currentIndex] = value;
  37.  
  38. if (_currentSize < _maxSize) {
  39. _currentSize++;
  40. } else {
  41. _startIndex = (_startIndex + 1) % _maxSize;
  42. }
  43. }
  44.  
  45. // Get the rolling average for the current data set.
  46. // If the data set is not full, return null
  47. public function getAverage() as Float? {
  48. if (_currentSize == 0) {
  49. return null;
  50. }
  51.  
  52. if (RETURN_NULL_WHEN_ROLLING_AVERAGE_HAS_INCOMPLETE_DATA && _currentSize < _maxSize) {
  53. return null;
  54. }
  55.  
  56. var total = 0;
  57. for (var i = 0; i < _currentSize; i++) {
  58. total += _data[i];
  59. }
  60. return total.toFloat() / _currentSize;
  61. }
  62. }
  63.  
  64. class MyDataFieldView extends WatchUi.DataField {
  65. // ...
  66. var _power3s as RollingAverage = new RollingAverage(3); // member variable
  67. var _power3sAverage as Float?; // member variable
  68. // ...
  69.  
  70. function initialize() {
  71. DataField.initialize();
  72. // ...
  73. }
  74.  
  75. function compute(info as Activity.Info) as Void {
  76. // ...
  77. if (info has :currentPower) {
  78. var power = info.currentPower;
  79. _power3s.addValue(power);
  80.  
  81. _power3sAverage = _power3s.getAverage();
  82. System.println("3s power = " + _power3sAverage);
  83. }
  84. // ...
  85. }
  86.  
  87. function onUpdate(dc as Dc) as Void {
  88. // ...
  89. if (_power3sAverage != null) {
  90. var power3sAverageFormatted = _power3sAverage.format("%.2f"); // format with 2 decimal places - e.g. "123.45"
  91. // draw _power3sAverage on the screen
  92. dc.drawText(x, y, Graphics.FONT_LARGE, power3sAverageFormatted, Graphics.TEXT_JUSTIFY_CENTER | Graphics.TEXT_JUSTIFY_VCENTER);
  93. } else {
  94. // draw "--" on the screen
  95. dc.drawText(x, y, Graphics.FONT_LARGE, "--", Graphics.TEXT_JUSTIFY_CENTER | Graphics.TEXT_JUSTIFY_VCENTER);
  96. }
  97. // ...
  98. }
  99. }
  100.  
Advertisement
Add Comment
Please, Sign In to add comment
Advertisement