{"id":41,"date":"2004-06-14T07:29:18","date_gmt":"2004-06-14T12:29:18","guid":{"rendered":"http:\/\/www.tigoe.com\/pcomp\/code2\/category\/arduinowiring\/41"},"modified":"2007-08-07T09:29:43","modified_gmt":"2007-08-07T14:29:43","slug":"analog-smoothing-algorithm","status":"publish","type":"post","link":"https:\/\/www.tigoe.com\/pcomp\/code\/arduinowiring\/41\/","title":{"rendered":"Analog Smoothing Algorithm"},"content":{"rendered":"<p>\nHere&#8217;s another simple algorithm for smothing analog values. This one was posted by Brian Taylor on the <a href=\"http:\/\/www.picbasic.co.uk\/forum\/index.php?s=8920dfc9d9691ec5d78bbeeaf7fdb6c2\" target=\"other\">PicBasic list<\/a>. <\/p>\n<p>\nAdjust alpha for more or less smoothing.  A large alpha takes much longer to reach final value. 1 =  no smoothing.  4 or 5 would typically give good results, but your mileage may vary.\n<\/p>\n<p><!--more--><\/p>\n<pre>\nnewVal var word        ' the value from the ADC \nsmoothed var word    ' a nicely smoothed result \n\nif newval > smoothed then\n        smoothed = smoothed + (newval - smoothed)\/alpha\nelse\n        smoothed = smoothed - (smoothed - newval)\/alpha\nendif\n<\/pre>\n<p>Here&#8217;s a more fully-developed example of it in Wiring syntax (tested on an Arduino board):\n<\/p>\n<pre>\n\/*\n  Analog smoothing algorithm\n by Tom Igoe\n \n This program reads an analog input and smooths out the result by averaging \n the result with past values of the analog input.\n\n  uses a potentiometer on analog in 2 to generate the value for alpha,\n  the number of samples to average.\n\n \n n.b. the variable \"smoothed\" needs to be a global, since it's modified \n each time a new smoothing is done.  So if you want to use this for multiple \n inputs, you'll need a \"smoothed\" variable for each input.\n \n Created 17 October 2005\n Updated 24 March 2006\n \n *\/\n\n\nint analogVal = 0;      \/\/ the value from the ADC \nint smoothed = 0;    \/\/ a nicely smoothed result. This needs to be a global variable\nint alpha = 4;       \/\/ the number of past samples to average by\n\n\/\/ function prototypes:\nvoid blink(int howManyTimes);\nvoid smoothValue(int rawValue);\n\nvoid setup() {\n  Serial.begin(9600);\n  blink(3);\n}\n\nvoid loop() {\n  \/\/ read the trimmer pot, use it to generate alpha:\n  alpha = (analogRead(1) \/114) + 1;\n  \/\/ get an analog reading:\n  analogVal = analogRead(0); \n  \/\/ smooth it:\n  smoothValue(analogVal);\n  \n  \/\/ to see the difference, try outputting analogVal\n  \/\/ instead of smoothed here, and graph the difference.\n  \/\/ divide by 4 to print the result as a byte:\n  Serial.print(smoothed\/4, BYTE);\n\n  \/\/ delay before next reading\n  delay(10);\n}\n\n\/\/ Blink the reset LED:\nvoid blink(int howManyTimes) {\n  int i;\n  for (i=0; i&lt; howManyTimes; i++) {\n    digitalWrite(13, HIGH);\n    delay(200);\n    digitalWrite(13, LOW);\n    delay(200);  \n  }\n}\n\n\/\/ Smooth out an analog reading:\nvoid smoothValue(int rawValue) {\n  if (rawValue &gt; smoothed) { \n    smoothed = smoothed + (rawValue - smoothed)\/alpha;\n  } \n  else {\n    smoothed = smoothed - (smoothed - rawValue)\/alpha;\n  }\n}\n\n\n\n<\/pre>\n<p>Written in PicBasic Pro, tested on a PIC 18F252:<\/p>\n<pre>\n\n'  Analog smoothing algorithm\n' by Tom Igoe\n \n' This program reads an analog input and smooths out the result by averaging \n' the result with past values of the analog input.\n\n' uses a potentiometer on analog in 2 to generate the value for alpha,\n' the number of samples to average.\n \n' n.b. the variable \"smoothed\" needs to be a global, since it's modified \n' each time a new smoothing is done.  So if you want to use this for multiple \n' inputs, you'll need a \"smoothed\" variable for each input.\n \n' Created 17 October 2005\n' Updated 27 March 2006\n \n \n ' Define ADCIN parameters\nDEFINE  ADC_BITS        10     ' Set number of bits in result\nDEFINE  ADC_CLOCK       3     \t' Set clock source (3=rc)\nDEFINE  ADC_SAMPLEUS    50    \t' Set sampling time in uS\n\nTRISA = %11111111       ' Set PORTA to all input\nADCON1 = %10000010      ' Set PORTA analog and right justify result\n\n\nanalogVal var word    '  the value from the ADC \nsmoothed var word     '  a nicely smoothed result. This needs to be a global variable\nbyteVar var byte      ' a byte variable to send out serially\nalpha var byte        '  the number of past samples to average by\ntrimPotValue var word ' the trimmer pot input\n\n' serial variables and constants:\ntx var portc.6\nrx var portc.7\ninv9600 con 16468\n\n'   Variables for subroutines:\ni var byte\nLEDPin var portb.7\n\ngosub blink\n\nmain:\n  ' read the trim pot to determine alpha between 1 and 10:\n  adcin 1, trimPotValue\n  alpha = (trimPotValue \/ 114) + 1\n  '  get an analog reading:\n  adcin 0, analogVal\n  '  smooth it:\n  gosub smoothValue\n  \n  '  to see the difference, try outputting analogVal\n  '  instead of smoothed here, and graph the difference.\n  '  divide by 4 to print the result as a byte:\n  byteVar = smoothed \/4\n  serout2 tx, inv9600, [byteVar]\n  \n  '  delay before next reading\n  pause 10\ngoto main\n\n'  Blink the reset LED:\nblink:\n  for i=0 to 3\n    high LEDPin\n    pause 200\n    low LEDPin\n    pause 200  \n  next\nreturn\n\n'  Smooth out an analog reading:\nsmoothValue:\n  if (analogVal > smoothed) then\n    smoothed = smoothed + (analogVal - smoothed)\/alpha\n  else \n    smoothed = smoothed - (smoothed - analogVal)\/alpha\n  endif\nreturn\n<\/pre>\n","protected":false},"excerpt":{"rendered":"<p>\/\/ divide by 4 to print the result as a byte: Serial.print(smoothed\/4, BYTE); \/\/ delay before next reading delay(10);}\/\/ Blink the reset LED:void blink(int howManyTimes) { int i; for (i=0; i&lt; howManyTimes; i++) { digitalWrite(13, HIGH); delay(200); digitalWrite(13, LOW); delay(200); }}\/\/ Smooth out an analog reading:void smoothValue(int rawValue) { if (rawValue &gt; smoothed) { smoothed = smoothed + (rawValue &#8211; smoothed)\/alpha; } else { smoothed = smoothed &#8211; (smoothed &#8211; rawValue)\/alpha; }}Written in PicBasic Pro, tested on a PIC 18F252:&#8217; Analog smoothing algorithm&#8217; by Tom Igoe &#8216; This program reads an analog input and smooths out the result by averaging &#8216; the result with past values of the analog input.&#8217;<\/p>\n<p>&#8230;This needs to be a global variablebyteVar var byte &#8216; a byte variable to send out seriallyalpha var byte &#8216; the number of past samples to average bytrimPotValue var word &#8216; the trimmer pot input&#8217; serial variables and constants:tx var portc.6rx var portc.7inv9600 con 16468&#8242; Variables for subroutines:i var byteLEDPin var portb.7gosub blinkmain: &#8216; read the trim pot to determine alpha between 1 and 10: adcin 1, trimPotValue alpha = (trimPotValue \/ 114) + 1 &#8216; get an analog reading: adcin 0, analogVal &#8216; smooth it: gosub smoothValue &#8216; to see the difference, try outputting analogVal &#8216; instead of smoothed here, and graph the difference.<\/p>\n","protected":false},"author":2,"featured_media":0,"comment_status":"closed","ping_status":"closed","sticky":false,"template":"","format":"standard","meta":{"footnotes":""},"categories":[9,10],"tags":[],"class_list":["post-41","post","type-post","status-publish","format-standard","hentry","category-arduinowiring","category-picbasic-pro"],"_links":{"self":[{"href":"https:\/\/www.tigoe.com\/pcomp\/code\/wp-json\/wp\/v2\/posts\/41","targetHints":{"allow":["GET"]}}],"collection":[{"href":"https:\/\/www.tigoe.com\/pcomp\/code\/wp-json\/wp\/v2\/posts"}],"about":[{"href":"https:\/\/www.tigoe.com\/pcomp\/code\/wp-json\/wp\/v2\/types\/post"}],"author":[{"embeddable":true,"href":"https:\/\/www.tigoe.com\/pcomp\/code\/wp-json\/wp\/v2\/users\/2"}],"replies":[{"embeddable":true,"href":"https:\/\/www.tigoe.com\/pcomp\/code\/wp-json\/wp\/v2\/comments?post=41"}],"version-history":[{"count":0,"href":"https:\/\/www.tigoe.com\/pcomp\/code\/wp-json\/wp\/v2\/posts\/41\/revisions"}],"wp:attachment":[{"href":"https:\/\/www.tigoe.com\/pcomp\/code\/wp-json\/wp\/v2\/media?parent=41"}],"wp:term":[{"taxonomy":"category","embeddable":true,"href":"https:\/\/www.tigoe.com\/pcomp\/code\/wp-json\/wp\/v2\/categories?post=41"},{"taxonomy":"post_tag","embeddable":true,"href":"https:\/\/www.tigoe.com\/pcomp\/code\/wp-json\/wp\/v2\/tags?post=41"}],"curies":[{"name":"wp","href":"https:\/\/api.w.org\/{rel}","templated":true}]}}