Solved - PING alternative HC-SR04 coding problem!
Jorge P
Posts: 385
Hi all, it's been quite a while since I used the propeller and I've run into a coding problem while trying to get the HC-SR04 working. Here is my code so far, some of it borrowed from other locations.
I have it running but either my timing is wrong or my distance calculations are wrong.
HC-SR04 Product Page
HC-SR04 datasheet
I am getting unexpected measurement results and modified the code somewhat while trying to figure it out.
Thanks in advance.
I have it running but either my timing is wrong or my distance calculations are wrong.
HC-SR04 Product Page
HC-SR04 datasheet
I am getting unexpected measurement results and modified the code somewhat while trying to figure it out.
Thanks in advance.
{{ Sparkfun's HC-SR04 Ultrasonic Sensor on the Propeller :) I've only seen this in C code for the Propeller so here it is in SPIN. }} CON _clkmode = xtal1 + pll16x _xinfreq = 5_000_000 TRIG = 1 ' Connected to P1 ECHO = 0 ' Connected to P0 HIGH = 1 LOW = 0 INPUT = 0 OUTPUT = 1 MAX_DIST = 23_200 DEBUG = 1 ' 1 = true, 0 = false ' from Timing.spin _10us = 1_000_000 / 10 ' Divisor for 10 us _1ms = 1_000_000 / 1_000 ' Divisor for 1 ms _1s = 1_000_000 / 1_000_000 ' Divisor for 1 s ' from dualPing.spin TO_IN_std = 74_641 ' std atmosphere speed of sound, us per inch traveled @ 59F air temperature TO_CM_std = 29_386 ' std atmosphere speed of sound, us per cm traveled @ 59F air temperature OBJ pst : "Parallax Serial Terminal" VAR LONG pulse_Start LONG pulse_Stop ' from Timing.spin LONG delay LONG syncpoint LONG clkcycles PUB Main | Microseconds, Distance, cnt1, cnt2 waitcnt(clkfreq * 5 + cnt) pst.start(115200) ' set pin directions OUTA[TRIG] := HIGH ' Direction not set but set the state low DIRA[TRIG] := OUTPUT ' Set to Output OUTA[TRIG] := LOW ' Ensure it is still Low DIRA[ECHO] := INPUT ' Set the echo input IF DEBUG == 1 pst.Str(STRING("Directions Set, ready for testing!")) NL REPEAT ' main loop OUTA[TRIG] := HIGH pause10us(1) OUTA[TRIG] := LOW WAITPNE(0, |< ECHO, 0) cnt1 := CNT WAITPEQ(0, |< ECHO, 0) cnt2 := CNT Microseconds := (||(cnt1 - cnt2) / (CLKFREQ / 1_000_000)) >> 1 if DEBUG == 1 pst.Home pst.ClearEnd pst.Dec(Microseconds) pst.Str(STRING(" us. ")) Distance := Microseconds / 58 IF DEBUG == 1 pst.Dec(Distance) pst.Str(STRING(" cm.")) pause1ms(100) PUB Inches(ms) : Distance ''Measure object distance in inches Distance := ms * 1_000 / TO_IN ' Distance In Inches PUB Centimeters(ms) : Distance ''Measure object distance in centimeters Distance := Millimeters(ms) / 10 ' Distance In Centimeters PUB Millimeters(ms) : Distance ''Measure object distance in millimeters Distance := ms * 10_000 / TO_CM ' Distance In Millimeters 'from dualPing.spin PUB calibrate(Tamb) ''Adjust Ping))) calibration constants to reflect ambient ''temperature impact on speed of sound (temperature assumed to be °F) Tamb += 460 TO_IN := TO_IN_std * (^^(Tamb * 1_000_000)) / (^^518_690_000) TO_CM := TO_IN * TO_CM_std / TO_IN_std 'From Timing.spin PUB pause10us(period) '' Pause execution for period (in units of 10 us) clkcycles := ((CLKFREQ / _10us * period) - 4296) #> 381 ' Calculate 10 us time unit WAITCNT(clkcycles + CNT) ' Wait for designated time 'From Timing.spin PUB pause1ms(period) '' Pause execution for period (in units of 1 ms). clkcycles := ((CLKFREQ / _1ms * period) - 4296) #> 381 ' Calculate 1 ms time unit WAITCNT(clkcycles + CNT) ' Wait for designated time 'From Timing.spin PUB pause1s(period) '' Pause execution for period (in units of 1 sec). clkcycles := ((CLKFREQ / _1s * period) - 4296) #> 381 ' Calculate 1 s time unit WAITCNT(clkcycles + CNT) ' Wait for designated time 'From Timing.spin PUB marksync10us(period) delay := (CLKFREQ / _10us * period) #> 381 ' Calculate 10 us time unit syncpoint := CNT 'From Timing.spin PUB waitsync WAITCNT(syncpoint += delay) PRI NL pst.NewLine PRI CLS pst.Clear DAT '-----------[ Predefined variables and constants ]----------------------------- TO_IN LONG 74_641 ' TO_CM LONG 29_386
Comments
Ping idles low and asserts high.
Yes, according to its datasheet it is.
And just to clarify, I am getting results but I can only detect readings between 2 and 6 centimeters. it should be more between 2 and 400 according to the specifications so I think some timing calculations, I have are off, which should be more apparent to someone with more experienced with spin than I am.