Is it really possible to accurately measure to .001?

Reply #59 and still you post no code! Nor any schematics.
Is their something you want to hide?

evaneazer:
I have to say that I'm having a hard time understanding the Infrared stuff. I have an emitter and sensor but it's behavior is not as easy to understand as my laser/photoresister. I'm not giving up!

Shouldn't be that hard to understand.

Modulated IR is just a fast blinking LED (e.g. 38000 times per second).
A tiny blinking light is easier to detect in a brigh environment than a tiny constant light.
And the blinking part can be amplified without amplifying the constant (day) light.

A 3-pin receiver contains all the electronis to receive/amplify/demodulate the blinking,
and outputs a LOW when modulated IR is received and a HIGH when not.
Leo..

Wireless will introduce unpredictable delays of way more than 1ms, making your required accuracy impossible to achieve.

Bluetooth also doesn't have a 300-meter range.

wvmarle:
Wireless will introduce unpredictable delays of way more than 1ms, making your required accuracy impossible to achieve.

Bluetooth also doesn't have a 300-meter range.

The HC-12 pdf mentions 4ms as 'fastest' for one byte, but only the mode, not the baud rate.
I suppose that has to be checked with a scope.

I don't think OP has mentioned BT. The HC-12 is 'intelligent' 433Mhz.
Leo..

Grumpy_Mike:
Reply #59 and still you post no code! Nor any schematics.
Is their something you want to hide?

Not hiding anything. My questions aren't really about code. But hey I've been wrong before. To be honest I do hope you find an issue. Here is the basic code for my testing apparatus I've mentioned. This IS NOT the code for my actual starting line/finish line set up. I don't have schematics. Can't draw what I don't understand...yet.

/* This code measures the elapsed time between rotations of a disk with a hole in it mounted directly
*  to a geared dc motor powered by a separate Arduino nano.  A red laser shines through the hole onto an LDR (with red filter) connected to another Arduino Nano.  
*  When the light hits the sensor, timer starts, when it hits again, the timer stops.  Rotations are between .6 seconds and 1.5 seconds depending on the voltage I send to the motor.  I measure ambient light 
*/

unsigned long startTime;  //time when laser beam hits the LDR first time
unsigned long stopTime;   //time when laser beam hits the LDR second time

void setup() {
 Serial.begin (9600);
 pinMode (A1,INPUT);
}

void loop() {

if(analogRead(A1)>100) {  //If the LDR sees the laser beam and goes above ambient light
 startTime=micros();     // start the timer
 delay(200);            // wait for beam to get blocked again. Debounce sort of
  int loopBreaker=1;  //probably a better way to do this but makes sense to me
 while (loopBreaker==1) { //waiting for the 
   if(analogRead(A1)>100) { //waiting for second pass of the hole in the spinning disc
     stopTime=micros();  //stop the timer
     loopBreaker=0;  //allow the while loop to end
     unsigned long elapsedTime =stopTime-startTime;  //calculate elasped time in microseconds
     float floatElapsedTime= (float) elapsedTime;  //convert elapsed time to a float for printing
     Serial.println(floatElapsedTime/1000000.0,4);  //convert to seconds and print
     delay(200);  //wait for beam to get blocked again.  Debounce sort of
   } //end of if
 }//end of while
} //end of if
}// end of void loop

I assumed it's Bluetooth from the HC- part number. Same as for common Bluetooth modules.

evaneazer:
I don't have schematics. Can't draw what I don't understand...yet.

How can you be sure you're wiring up your components correctly if you don't know enough about them to draw it out?

Why are you using analogRead() ? Each call to analogRead() takes about 100 microsecs so straight away you have at least 100 microsecs of "delay" in your code.

Just use the optical detector as a digital device and use digitalRead(). Better still for precise timing, connect the input to one of the external interrupt pins and use an interrupt service routine to record the time.

Nowhere in your code do you check that the signal has fallen between readings. If you use a RISING interrupt it will automatically take care of that.

Have a look at this program that detects the intervals between pulses

// simple program to determine interval between successive RISING pulses

// variables for ISR
volatile unsigned long isrPulseMicros = 0;
volatile unsigned long isrPulseCount = 0;
volatile bool newPulseMicros = false;

// pulse variables
byte pulsePin = 2;
unsigned long prevPulseMicros;
unsigned long latestPulseMicros;
unsigned long pulseInterval;
unsigned long pulseCount;


// time variables for display
unsigned long prevShowMillis;
unsigned long showIntervalMillis = 1000;


void setup() {
    Serial.begin(115200);
    Serial.println("Starting PulseIntervalDemo.ino");
    attachInterrupt(digitalPinToInterrupt(pulsePin), revMicrosISR, RISING);
}

void loop() {

    if (newPulseMicros == true) {
            // save the previous value
        prevPulseMicros = latestPulseMicros;
            // disable interrupts briefly while we read the data
        noInterrupts();
            latestPulseMicros = isrPulseMicros;
            pulseCount = isrPulseCount;
            newPulseMicros = false;
        interrupts();
            // calculate the interval
        pulseInterval = latestPulseMicros - prevPulseMicros;
    }
        // this time check is just to reduce the amount of output on the Serial Monitor
    if (millis() - prevShowMillis >= showIntervalMillis) {
        prevShowMillis += showIntervalMillis;
        Serial.print("Pulse Interval micros ");
        Serial.print(pulseInterval);
        Serial.print("  ----   Pulse Count ");
        Serial.println(pulseCount);
    }

}

void revMicrosISR() {
        isrPulseMicros = micros();
        isrPulseCount ++;
        newPulseMicros = true;
}

...R

Edited to add example program

Wawa:
The biggest problem will be linking the start and finish lines.
Wireless could have a delay of several ms. No experience there.
HC-12 modules have some info, but I could not find it in datasheets of other modules.
Leo..

Agreed, Any solution involving Serial communication will be too slow and the OP's idea to send a test transmission and subtract the result will not be accurate enough.

I have been pondering a similar project and the best idea that I have come up with so far is to use 2 arduino's connected by RS485 modules. Instead of using Serial just have an interrupt that affects a pin change that in turn triggers an interrupt on the second arduino. This would have the lowest latency that I can think of.

What say you?

Les

Latency is not so much the problem. Unknown/unpredictable latency is, and that's inherent to most if not all wireless solutions. No problem if you're trying to measure time in the seconds, maybe no problem if it's in the tenth of seconds, it's almost certainly a problem for millisecond accuracy.

Serial may be able to get the job done - if the transmission takes the same amount of time every time it's used.

Indeed all you need is a single bit worth of information, so a change of state should be enough. For the distance, a wire and current based signal is the way to go. The receiving end only needs a single resistor (to create the required high/low voltage signal). The sending side needs a little more as that's the side producing the current. The interrupt based solution should work with such a system.

I would say that

Serial.println(floatElapsedTime/1000000.0,4);  //convert to seconds and print

Quantities your error and gives you a false indication of your repeatability.

This sketch uses micros to measure in minutes and seconds to four decimal places.
Maybe you can adapt it to your needs.
nowMicros should then ofcourse be the micros between start and finish.
Leo..

unsigned long nowMicros;
unsigned int seconds, secondsRemaining, runMillis;
byte runHours, runMinutes, runSeconds;
boolean printed = false;
char buf[21];

void setup() {
  Serial.begin(9600);
  Serial.println("Stopwatch");
}

void loop() {
  nowMicros = micros();
  seconds = nowMicros / 1000000;
  runHours = seconds / 3600;
  secondsRemaining = seconds % 3600;
  runMinutes = secondsRemaining / 60;
  runSeconds = secondsRemaining % 60;
  runMillis = nowMicros / 100 % 10000; // for four decimal places
  sprintf(buf, "Runtime: %02d:%02d:%02d.%04d\n", runHours, runMinutes, runSeconds, runMillis);
  Serial.print(buf);
  while (runHours > 0) { // micros() rolls over at ~70minutes | wait here if stopwatch runs more than 1hour
    if (!printed) {
      Serial.println("Overflow");
      printed = true;
    }
  }
  delay(1000); // total sample interval is this delay plus some calculating/printing time
}

wvmarle:
Wireless will introduce unpredictable delays of way more than 1ms, making your required accuracy impossible to achieve.

Bluetooth also doesn't have a 300-meter range.

For what it's worth, post 20 of this thread describes a wireless approach using the cheap 433 MHz modules where I got synchronization to about 55 microseconds without optimization: Communication Between 2 Ultrasonic Sensors - Project Guidance - Arduino Forum

It would surprise me if one could get reliable 300 meter range out of it, but pretty tight synchronization with low level access to the transmitter and receiver should be possible.

The HC-12, as Wawa notes, is a "smart radio", which is to say there's another microcontroller in the path that has an unknown effect on the message latency. There exists a project to hack the HC-12 microcontroller here, which gives some information on the low level operations, but this part of the project is incomplete and hasn't moved in the last 6 months or so. Without modifying the HC-12, sub-millisecond synchronization seems unlikely.

Thanks for sharing this.
433Mhz/300m shouldn't be a big issue if yagi aerials are used.
Leo..

It looks like we lost the OP a long time ago.

The comments in Reply #71 are interesting - I have bookmarked the link

...R

In reading the OP notes and the posts, it seems that the actual problem has not been completely defined.

a soap box race, down a mountain, can be from 1,000 meters to 4,000 meters and is the width of a roadway that is 2 lanes, plus shoulder. this would allow for 2 racers on the course at the same time.

start and finish are not line of sight.

cart speeds in excess of 60 MPH have been recorded in the Cairngorm Soapbox Extreme course.

the OP stated that he does not think any timers available can accurately time a race.

now for my assumptions.
races of 50 carts would be more like single cart timed races, with the best time taking the prize. the races would not be 10 carts and the first to cross wins. with this information, the actual timing is crucial.

based on measuring anything, the 'actual' time or distance or temperature is not as important as repeatability. (taken to the extreme) if the timer were off by a few minutes, but could time every racer to 0.0001 seconds, that would be a fair and honest race timer.

to that end, the actual time of the start is not nearly as important as the repetitive signal that the race started. time of flight for the radio waves could be allowed for (or not) but the time of the start to the start of the timing at the finish line would need to be repetitive. to within the OP's 0.001 seconds.

the beam break of 10 meters span is a separate issue. my garage door has a sensor that is a beam break, and they make driveway beam break sensors.
I have never bothered to time them.

but we come back to repeatability being the more important factor. if it takes 0.7001 seconds to respond to a beam break, but it ALWAYS takes 0.7001 seconds, every time, then the accuracy is within the criteria of the needed accuracy.

as a note, machinists have known for decades that a warm or cold micrometer will be off, and the temperature of the part also effects the measurement. that is why clean rooms of regulated temperature are created.

my wild guess would be that a start signal, generated at mid-course would reach both start and finish at approximately the same time.
the stepper at the start could raise the flag, or a light could be turned on like in drag racing.

OP wanted to do this for training sessions, to optimise their wheeled soapbox and make it faster, not for use in a race.

wvmarle:
OP wanted to do this for training sessions, to optimise their wheeled soapbox and make it faster, not for use in a race.

I guess when he stated it was for a race timer, I just figured.....
but if you are making the need more precice by saying that he wants repeatability, then the start timer and actual timer are irrelevent, as long as the time between the start signal and the finish signal are consistant and repetitve.
if you start over your prescribed course, and 5.078126 seconds later the finish line timer gets the start value. and it is always 5.078126 second delay, then the overall time on the course will reflect what the competitor is doing. so, if holding your finger up adds time to the overall and using a visor reduces the overall time, then the device would help to identify the things that slow the soap box and that speed it up.

When the general public don't understand systematic vs random error...

dave-in-nj:
but if you are making the need more precice by saying that he wants repeatability, then the start timer and actual timer are irrelevent, as long as the time between the start signal and the finish signal are consistant and repetitve.

That's what I was trying to say in Reply #45

...R

Robin2:
That's what I was trying to say in Reply #45

...R

IMHO, when a thread gets to 40 posts and the general concepts are not defined, then the actual engineering is lost in the clutter.
you, jremington, Wawa, DaveEvans and Grumpy_Mike said all that was needed to say in the first dozen posts. and even some of that was repeated.
as a side note, I do not think many people understand that a stepper is like a sprinter running in a race. you have them run in a cadence and they move like the wind. you have them take 3 steps, then stop, you go check some sensor, then come back and pick up running where you left off, run for 3 steps, or 30 steps, stop, go turn on a light, check to see if a switch has changed state, test the encoder for distance, come back, pick up where you left off......
also, in this case, I never understood exactly how he used the stepper. was he spinning it at a constant rate to test the time of rotation ? if so, was that driven by a signal generator or by software ? was he starting the stepper to signal the start of the race and timing the light sensor as the gear rotated ?
it would seem to me that a ball dropped would travel at speed based on the density of the air. but, generally speaking, one could drop a ball from the top of the second floor, break a beam sensor at that point, then break a second beam sensor at the floor of the first floor and have a time that would be able to be measured and would be repetitive. not sure if atmospheric density would affect the time with changes such as humidity or barometric pressures from one day to the next of even over a few hours.....
as for dropping balls, there are hundreds of marble machines showing how to drop balls on youtube.