Hello everybody!

Im working on a project involving a spedometer but im not getting the expected results in the tinkercad circuits simulation..

The circuit is simplified down to two components, a function generator (used instead of a hall trigger) to simulate a wheel rotation detection, and a arduino.

I shared the circuit in question below, so feel free to check it out and see if you can make sense of it, because i sure cant..

Now, if a wheel circumference (variable name "cirq" in the code) is set to 2114 mm, and the function generator is set to 1Hz (one wheel rotation per second), the speed SHOULD be 7.6104 km/h, but the simulator returns 7.2km/h.

if the frequency is increased to 2Hz, the result is 14.4km/h, but should be 15.2208km/h.

Now, if we change the "cirq" to 2000(mm), the simulator suddenly reports expected speed, 7.2km/h @ 1Hz and 14.4km/h @ 2Hz.

But the simulator fails if the cirq is anything more precies than increments of 1000.

Also, the simulator fails to calculate correct speed if the function generator is set to 1.5Hz or some other decimal number..

So am i doing something wrong here? Is my code incorrect or is it the simulator that is misbehaving?

• mehdi apollo

hi,

Floating point is quite tricky in Arduino.

in line number 73 the division of 2 values are returning a hole number making the speedmms variable = 2, and in line 74 you are multiplying this 2 with 3.6 making the value for variable speed = 7.2 which is giving you the speed. of 7.2km/h.

i have made a change in line 73 to " float speedmmms = (float(distance) / float(elapsedTime)); // speed = mm/mS"

this now gives me an accurate result up to 2 decimal points. 7.61 km/h @ 1 hz and 15.22 @ 2 hz

to get the result to 4 decimal point change the code in line number 14 2 "#define writeVarSerial(prefix,value,sufix) Serial.println(STR_BLANK); Serial.print(prefix); Serial.print(value,4); Serial.println(sufix);" I have added only "4" with "Serial.print(value).

this now gives the result to 4 digits but its not accurate the values are 7.6028km/h @ 1 hz but it should be 7.6104 km/h?

this time i have changed in line number 74 "speed = float(speedmmms) * 3.6;" this now gives me the accurate result as expected

7.6104km/h @ 1Hz and 15.2208km/h @ 2 Hz

Thankx

• Spammy Liggist

Thank you SO VERY MUCH(!!!) for your assistance!

From what i gather, the only real difference was to specify (float(value) / (float(value2), even though the value/value2 were defined as float in global scope..

I really dont NEED this kind of precision (i mean, current speed with 4 decimals?? :D ), but the autistic part of me can rest peacefully now that i know my code wasnt really wrong,it was just a minor implementation error. :)

Btw, the lines youre refering to, 73 and 74 was originally a single line, but i split up the calculation to try and pinpoint my problem.

My speedcalc function now looks like this:

void doSpeedCalc(void) {
noInterrupts();
uint16_t _rotCount = rotCount;
uint32_t _rotTime = rotTime;
interrupts();
if (_rotCount) {
if (checkElapsed(_rotTime,(3000 * _rotCount))) {
noInterrupts();
rotCount = 0;
rotTime = 0;
speed = 0.0;
interrupts();
}
}
if (_rotCount >= numRotToMeasure) {
noInterrupts();
rotCount = 0;
rotTime = 0;
interrupts();
uint32_t elapsedTime = 0;
uint32_t distance = (cirq * (_rotCount));
elapsedTime = (NOW - _rotTime);
// speed = distance / time
speed = ((float(distance) / float(elapsedTime)) * 3.6); // line 73 & 74 mentioned in Mehdi Hassans reply above
}
if (checkElapsed(lastSpdRep,spdRepInterval)) {
lastSpdRep = NOW;
printSpeed();
}
}
• mehdi apollo

Its good to hear it worked to meet your expectations. good lluck with tinkercad

thanx