Skateboard slalom timer

Hi,
I’m having fun and frustrations learning Arduino. My goal is to build a timing system for slalom skateboarding, at the same time learn.
I understand a lot of the principles and have been reading (alot of this forum), googling and youtubeing, but when it come to actual programming, I seem to hit a block. A bit like maths…

Anyway the timer will comprise of 2 tapeswitches, hardwired to the arduino and lcd. Will concentrate on a single lane before doing dual lane.

So far I have found some code and put togther a LCD, start/stop button, reset button and a LED. The timer works and the led flashes when timing is going on and I get a readout in sec and ms (thousands) just as I want.

I’ll start off with with just a couple of questions and as the project comes along I’ll probably ask more.

  1. As for the start/stop button, how do I stop it registering a second press close to the first press The first set of wheels trigger the start of the timer and the button needs to be inactive as the rear wheels press the tape switch. Say a blanking time of 3 seconds?
    Or would it be better to split the start/stop button into 1 start and 1 stop button(tapeswitch) ?

  2. My timer runs, but nothing is displayed on the LCD until the the timer is stopped. Not a problem, but would be nice to see the timer running on the LCD “live” Need a bit of guidance.

Thank you in advance and hope I can learn in the process. Lots to implement like dual lane, random beep start, false start routine, printout to excel etc etc, but one step at a time…

#include <LiquidCrystal.h>


#define ledPin  10
#define startstopPin 6
#define resetPin 7

LiquidCrystal lcd(12, 11, 5, 4, 3, 2);

int value = LOW;                    // previous value of the LED
int buttonState;                    // variable to store button state
int stateReset;
int lastButtonState;                // variable to store last button state
int blinking;                       // condition for blinking - timer is timing
long interval = 100;                // blink interval - change to suit
long previousMillis = 0;            // variable to store last time LED was updated
long startTime ;                    // start time for stop watch
long elapsedTime ;                  // elapsed time for stop watch
int fractional;                     // variable used to store fractional part of time



void setup()
{
   Serial.begin(9600);

   pinMode(ledPin, OUTPUT);         // sets the digital pin as output

   pinMode(startstopPin, INPUT);       // not really necessary, pins default to INPUT anyway
   pinMode(resetPin, INPUT);
   digitalWrite(startstopPin, HIGH);   // turn on pullup resistors. Wire button so that press shorts pin to ground.
   digitalWrite(resetPin, HIGH);
   
   // set up the LCD's number of columns and rows: 
   lcd.begin(16, 2);
   // Print a message to the LCD.
   lcd.print("--Stop Watch--");
   lcd.setCursor(0, 1);
   lcd.print("System ready!");

}

void loop()
{
    // check for button press
   buttonState = digitalRead(startstopPin);                   // read the button state and store
   stateReset = digitalRead(resetPin);

   if (buttonState == LOW && lastButtonState == HIGH && blinking == false){     // check for a high to low transition
      // if true then found a new button press while clock is not running - start the clock

      startTime = millis();                                   // store the start time
      blinking = true;                                        // turn on blinking while timing
      delay(5);                                               // short delay to debounce switch
      lastButtonState = buttonState;      // store buttonState in lastButtonState, to compare next time
      
      lcd.clear();
      lcd.print("--Stop Watch--");
      lcd.setCursor(0, 1);
      lcd.print("Started timing!");
      
   }

   else if (buttonState == LOW && lastButtonState == HIGH && blinking == true){     // check for a high to low transition
      // if true then found a new button press while clock is running - stop the clock and report

        elapsedTime =   millis() - startTime;              // store elapsed time
        blinking = false;                                  // turn off blinking, all done timing
        lastButtonState = buttonState;                     // store buttonState in lastButtonState, to compare next time

       // routine to report elapsed time
        Serial.print( (int)(elapsedTime / 1000L));         // divide by 1000 to convert to seconds - then cast to an int to print

        Serial.print(".");                             // print decimal point

        // use modulo operator to get fractional part of time
       fractional = (int)(elapsedTime % 1000L);

       // pad in leading zeros - wouldn't it be nice if
       // Arduino language had a flag for this? :)
       if (fractional == 0)
          Serial.print("000");      // add three zero's
       else if (fractional < 10)    // if fractional < 10 the 0 is ignored giving a wrong time, so add the zeros
          Serial.print("00");       // add two zeros
       else if (fractional < 100)
          Serial.print("0");        // add one zero

       Serial.println(fractional);  // print fractional part of time
       
       // set the cursor to column 0, line 2
       // (note: line 1 is the second row, since counting begins with 0):
       lcd.clear();
       lcd.print("--Stop Watch--");
       
       lcd.setCursor(0, 0);      
       lcd.print("Run over! time:");
       
       lcd.setCursor(0, 1);
       lcd.print((int)(elapsedTime / 1000));
       lcd.print(":");
       
       //lcd.setCursor(10, 1);
       lcd.print(fractional);
       lcd.print(" ms");
   }

   else{
      lastButtonState = buttonState;                         // store buttonState in lastButtonState, to compare next time
   }
   
   if (stateReset == LOW) {
     blinking = false;
     lcd.clear();
     lcd.print("--Stop Watch--");
     lcd.setCursor(0, 1);
     lcd.print("System ready!");
  }

   // blink routine - blink the LED while timing
   // check to see if it's time to blink the LED; that is, the difference
   // between the current time and last time we blinked the LED is larger than
   // the interval at which we want to blink the LED.

   if ( (millis() - previousMillis > interval) ) {

      if (blinking == true){
         previousMillis = millis();                         // remember the last time we blinked the LED

         // if the LED is off turn it on and vice-versa.
         if (value == LOW)
            value = HIGH;
         else
            value = LOW;
         digitalWrite(ledPin, value);
      }
      else{
         digitalWrite(ledPin, LOW);                         // turn off LED when not blinking
      }
   }

}

1) As for the start/stop button, how do I stop it registering a second press close to the first press

You don't. You simply ignore a press that occurs too soon after a previous press. That means, of course, that you need to keep track of when the press(es) occur.

   if (buttonState == LOW && lastButtonState == HIGH && blinking == false){     // check for a high to low transition
      // if true then found a new button press while clock is not running - start the clock
   }
   else if (buttonState == LOW && lastButtonState == HIGH && blinking == true){

No!

Nested ifs are far easier to understand than this unrelated collection of conditions.

   if (buttonState == LOW && lastButtonState == HIGH)
   {     // Down here where it belongs
      // if true then found a new button press

      if(!blinking) // like a professional programmer
      {
      }
      else
      {

2) My timer runs, but nothing is displayed on the LCD until the the timer is stopped. Not a problem, but would be nice to see the timer running on the LCD "live" Need a bit of guidance.

Look at where you are displaying the data on the LCD. Only inside the "if switch became pressed and time is running" block.

You want to display the data on the LCD on every pass through loop, if time is running.

Thank you for the pointers and making me think.!

My level of programming, I understand (I think) what you are saying, just have to find out how to implement it.

Hi PaulS, I'm playing around, with your pointers but not having much luck.

You don't. You simply ignore a press that occurs too soon after a previous press. That means, of course, that you need to keep track of when the press(es) occur.

How, I've been looking for examples for days on how to do this but can't find anything.

Nested ifs are far easier to understand than this unrelated collection of conditions.

This code came off the Arduino playground. I can see that it all is a bit messy with bracket in the wrong places, However, I can't seem to get you bit of code to work. It just start timing without any press and the time adds up per press.

You want to display the data on the LCD on every pass through loop, if time is running.

Again, tried a lot, but I can get the timer to show running.

Any chance of showing me the correct complete code. I'm not trying to cheat, but with comparing it with my existing code I can learn on what goes where and how.

How, I've been looking for examples for days on how to do this but can't find anything.

The state change detection example shows you how to determine that a switch has become pressed (or released). Use millis() to get the time that that happened. If this time minus last time is a small value, ignore this change. Otherwise do something about it.

This code came off the Arduino playground.

Not all of it has been peer-reviewed. There are easier to understand ways of dealing with multiple conditions.

However, I can't seem to get you bit of code to work.

We need to see what you changed the code to.

Again, tried a lot, but I can get the timer to show running.

I'm assuming that that should be can't get the timer to show. Again, we need to see the code.

But, what should happen in loop is this: See if the start switch has become pressed. If so, set the elapsed time to 0 and record the fact that the timer is running. See if the stop switch has become pressed. If so, record the fact that the timer is not running. See if the timer is running. If so, display the elapsed time on the LCD.

Notice that there is no indentation there, to indicate that showing the time depends on the state of the switches. It depends only on whether the timer is running.

In the stop switch has become pressed case, you probably want to display something a bit different, to provide visual confirmation that the race is over (Total time: xx.xxx as opposed to Elapsed time: xx.xxx).

Any chance of showing me the correct complete code.

Not much. You'll learn a lot more by having us review your attempt(s).

Thank you.

Will have a fresh look at it tomorrow. my head hurts!

Not much. You'll learn a lot more by having us review your attempt(s).

Was worth a try :) Anyway, you are probably right. Will look into it...

More confused thn ever now…

#include <LiquidCrystal.h>


#define ledPin  10
#define startstopPin 6
#define resetPin 7

LiquidCrystal lcd(12, 11, 5, 4, 3, 2);

int value = LOW;                    // previous value of the LED
int buttonState;                    // variable to store button state
int stateReset;
int lastButtonState;                // variable to store last button state
int blinking;                       // condition for blinking - timer is timing
long interval = 100;                // blink interval - change to suit
long previousMillis = 0;            // variable to store last time LED was updated
long startTime ;                    // start time for stop watch
long elapsedTime ;                  // elapsed time for stop watch
int fractional;                     // variable used to store fractional part of time



void setup()
{
   Serial.begin(9600);

   pinMode(ledPin, OUTPUT);         // sets the digital pin as output

   pinMode(startstopPin, INPUT);       // not really necessary, pins default to INPUT anyway
   pinMode(resetPin, INPUT);
   digitalWrite(startstopPin, HIGH);   // turn on pullup resistors. Wire button so that press shorts pin to ground.
   digitalWrite(resetPin, HIGH);
   
   // set up the LCD's number of columns and rows: 
   lcd.begin(16, 2);
   // Print a message to the LCD.
   lcd.print("--Stop Watch--");
   lcd.setCursor(0, 1);
   lcd.print("System ready!");

}

void loop()
{
    // check for button press
   buttonState = digitalRead(startstopPin);                   // read the button state and store
   stateReset = digitalRead(resetPin);

    if (buttonState == LOW && lastButtonState == HIGH)
   {     // Down here where it belongs
      // if true then found a new button press

      if(!blinking) // like a professional programmer
      {
      }
      else
      {
      startTime = millis();                                   // store the start time
      blinking = true;                                        // turn on blinking while timing
      delay(5);                                               // short delay to debounce switch
      lastButtonState = buttonState;      // store buttonState in lastButtonState, to compare next time
      
      lcd.clear();
      lcd.print("--Stop Watch--");
      lcd.setCursor(0, 1);
      lcd.print("Started timing!");
      
   }

   

        elapsedTime =   millis() - startTime;              // store elapsed time
        blinking = false;                                  // turn off blinking, all done timing
        lastButtonState = buttonState;                     // store buttonState in lastButtonState, to compare next time

       // routine to report elapsed time
        Serial.print( (int)(elapsedTime / 1000L));         // divide by 1000 to convert to seconds - then cast to an int to print

        Serial.print(".");                             // print decimal point

        // use modulo operator to get fractional part of time
       fractional = (int)(elapsedTime % 1000L);

       // pad in leading zeros - wouldn't it be nice if
       // Arduino language had a flag for this? :)
       if (fractional == 0)
          Serial.print("000");      // add three zero's
       else if (fractional < 10)    // if fractional < 10 the 0 is ignored giving a wrong time, so add the zeros
          Serial.print("00");       // add two zeros
       else if (fractional < 100)
          Serial.print("0");        // add one zero

       Serial.println(fractional);  // print fractional part of time
       
       // set the cursor to column 0, line 2
       // (note: line 1 is the second row, since counting begins with 0):
       lcd.clear();
       lcd.print("--Stop Watch--");
       
       lcd.setCursor(0, 0);      
       lcd.print("Run over! time:");
       
       lcd.setCursor(0, 1);
       lcd.print((int)(elapsedTime / 1000));
       lcd.print(":");
       
       //lcd.setCursor(10, 1);
       lcd.print(fractional);
       lcd.print(" ms");
   }

   else{
      lastButtonState = buttonState;                         // store buttonState in lastButtonState, to compare next time
   }
   
   if (stateReset == LOW) {
     blinking = false;
     lcd.clear();
     lcd.print("--Stop Watch--");
     lcd.setCursor(0, 1);
     lcd.print("System ready!");
  }

   // blink routine - blink the LED while timing
   // check to see if it's time to blink the LED; that is, the difference
   // between the current time and last time we blinked the LED is larger than
   // the interval at which we want to blink the LED.

   if ( (millis() - previousMillis > interval) ) {

      if (blinking == true){
         previousMillis = millis();                         // remember the last time we blinked the LED

         // if the LED is off turn it on and vice-versa.
         if (value == LOW)
            value = HIGH;
         else
            value = LOW;
         digitalWrite(ledPin, value);
      }
      else{
         digitalWrite(ledPin, LOW);                         // turn off LED when not blinking
      }
   }

}

More confused thn ever now...

I can completely understand that.

You are aware, I hope, that there is a menu on the IDE. One of the menu items is Tools. On that menu is one called Auto Format.

You REALLY need to make use of that tool.

While you are at it, put EVERY { on a new line.

          if(this == that)
          {
             // Do a bunch of stuff
          }

is much easier to see the range of than:

          if(this == that){
             // Do a bunch of stuff
          }

when there is a lot of code.

Now, suppose that we create a function to handle the blinking that this code does:

  if ( (millis() - previousMillis > interval) )
  {
    if (blinking == true)
    {
      previousMillis = millis();                         // remember the last time we blinked the LED

      // if the LED is off turn it on and vice-versa.
      if (value == LOW)
        value = HIGH;
      else
        value = LOW;
      digitalWrite(ledPin, value);
    }
    else
    {
      digitalWrite(ledPin, LOW);                         // turn off LED when not blinking
    }
  }

like so:

void blink()
{
  if ( (millis() - previousMillis > interval) )
  {
    if (blinking == true)
    {
      previousMillis = millis();                         // remember the last time we blinked the LED

      // if the LED is off turn it on and vice-versa.
      if (value == LOW)
        value = HIGH;
      else
        value = LOW;
      digitalWrite(ledPin, value);
    }
    else
    {
      digitalWrite(ledPin, LOW);                         // turn off LED when not blinking
    }
  }
}

When reading through what loop is doing, which of these version is easier to grasp?

void loop()
{
   // Do some stuff
   blink();
}

or:

void loop()
{
   // Do some stuff
  if ( (millis() - previousMillis > interval) )
  {
    if (blinking == true)
    {
      previousMillis = millis();                         // remember the last time we blinked the LED

      // if the LED is off turn it on and vice-versa.
      if (value == LOW)
        value = HIGH;
      else
        value = LOW;
      digitalWrite(ledPin, value);
    }
    else
    {
      digitalWrite(ledPin, LOW);                         // turn off LED when not blinking
    }
  }
}

Having functions makes the code much easier to debug. It's a divide and conquer process. Is the problem in a function, or in the way that the function is called in loop()? Is the function trying to do to much?

Suppose that you have a function called getTemp(), and that function reads a temperature sensor, blinks an LED, sends a text message, pats the dog, and gives your Mom a kiss. Now, is that a realistic set of things for a function to perform? No, of course not. Giving your Mom a kiss belongs in another function, so that you can call it more, or less, often than you call getTemp(), or under different circumstances.

You need to determine the major things that the loop() function is supposed to do, and create functions that perform each of those tasks. Move the code from loop() to the new function(s), replacing the code with a call to the function.

Your loop() function should have no more than a dozen lines that call other functions. That makes it so much easier to determine when a function is doing too much, doing something inappropriate, etc.

Ok, in bed with a stinking cold, so a bit of time to read and learn. (and format the code)

I now understand the (!blinking) instead of (… && blinking == false)

This now starts the timer as it should, so ok.
Now I need to look into stopping the timer with the correct code as I won’t stop as it is atm.
Should I be looking at the same for start push but opposite (blinking) ?

I really appreciate you helping and though it must be frustrating at my stabbing in the dark attempts!
I’m slowly getting there, but dosen’t help that I’m also dyslectic.

#include <LiquidCrystal.h>


#define ledPin  10
#define startstopPin 6
#define resetPin 7

LiquidCrystal lcd(12, 11, 5, 4, 3, 2);

int value = LOW;                    // previous value of the LED
int buttonState;                    // variable to store button state
int stateReset;
int lastButtonState;                // variable to store last button state
int blinking;                       // condition for blinking - timer is timing
long interval = 100;                // blink interval - change to suit
long previousMillis = 0;            // variable to store last time LED was updated
long startTime ;                    // start time for stop watch
long elapsedTime ;                  // elapsed time for stop watch
int fractional;                     // variable used to store fractional part of time



void setup()
{
  Serial.begin(9600);
  pinMode(ledPin, OUTPUT);            // sets the digital pin as output
  pinMode(startstopPin, INPUT);       // not really necessary, pins default to INPUT anyway
  pinMode(resetPin, INPUT);
  digitalWrite(startstopPin, HIGH);   // turn on pullup resistors. Wire button so that press shorts pin to ground.
  digitalWrite(resetPin, HIGH);

  // set up the LCD's number of columns and rows: 
  lcd.begin(16, 2);
  // Print a message to the LCD.
  lcd.print("--Stop Watch--");
  lcd.setCursor(0, 1);
  lcd.print("System ready!");

}

void loop()
{
  // check for button press
  buttonState = digitalRead(startstopPin);                   // read the button state and store
  stateReset = digitalRead(resetPin);

  if (buttonState == LOW && lastButtonState == HIGH)         // check for a high to low transition
  {                                                          // if true then found a new button press while clock is not running - start the clock
    if(!blinking)

    startTime = millis();                                   // store the start time
    blinking = true;                                        // turn on blinking while timing
    delay(5);                                                    // short delay to debounce switch
    lastButtonState = buttonState;                          // store buttonState in lastButtonState, to compare next time

    lcd.clear();
    lcd.print("--Stop Watch--");
    lcd.setCursor(0, 1);
    lcd.print("Started timing!");

  }

  else if (buttonState == LOW && lastButtonState == HIGH && blinking == true)  // check for a high to low transition
  {     
    // if true then found a new button press while clock is running - stop the clock and report

    elapsedTime =   millis() - startTime;              // store elapsed time
    blinking = false;                                  // turn off blinking, all done timing
    lastButtonState = buttonState;                     // store buttonState in lastButtonState, to compare next time

    // routine to report elapsed time
    Serial.print( (int)(elapsedTime / 1000L));         // divide by 1000 to convert to seconds - then cast to an int to print
    Serial.print(".");                                 // print decimal point

    // use modulo operator to get fractional part of time
    fractional = (int)(elapsedTime % 1000L);

    // pad in leading zeros - wouldn't it be nice if
    // Arduino language had a flag for this? :)
    if (fractional == 0)
      Serial.print("000");      // add three zero's
    else if (fractional < 10)    // if fractional < 10 the 0 is ignored giving a wrong time, so add the zeros
      Serial.print("00");       // add two zeros
    else if (fractional < 100)
      Serial.print("0");        // add one zero

    Serial.println(fractional);  // print fractional part of time

    // set the cursor to column 0, line 2
    // (note: line 1 is the second row, since counting begins with 0):
    lcd.clear();
    lcd.print("--Stop Watch--");

    lcd.setCursor(0, 0);      
    lcd.print("Run over! time:");

    lcd.setCursor(0, 1);
    lcd.print((int)(elapsedTime / 1000));
    lcd.print(":");

    //lcd.setCursor(10, 1);
    lcd.print(fractional);
    lcd.print(" ms");
  }


  else
  {
    lastButtonState = buttonState;                         // store buttonState in lastButtonState, to compare next time
  }

  if (stateReset == LOW) 
  {
    blinking = false;
    lcd.clear();
    lcd.print("--Stop Watch--");
    lcd.setCursor(0, 1);
    lcd.print("System ready!");
  }

  // blink routine - blink the LED while timing
  // check to see if it's time to blink the LED; that is, the difference
  // between the current time and last time we blinked the LED is larger than
  // the interval at which we want to blink the LED.

  if ( (millis() - previousMillis > interval) ) 
  {
    if (blinking == true){
      previousMillis = millis();                         // remember the last time we blinked the LED

      // if the LED is off turn it on and vice-versa.
      if (value == LOW)
        value = HIGH;
      else
        value = LOW;
      digitalWrite(ledPin, value);
    }
    else
    {
      digitalWrite(ledPin, LOW);                         // turn off LED when not blinking
    }
  }

}

Should I be looking at the same for start push but opposite (blinking) ?

Exactly.

Ok, been away, but looking again at this.
I have manged to include a serial LCD and added some LEDS.

Yellow for timer ready and red for timer stopped. A green led blinks when the timer is running.

Up until now, one button has been for both start and stop. (and a seperate reset button)
This set up works.

I’m now trying to change to one button for start (startPin 6) and another for stop (stopPin 8 )
However, the stop button starts the timer and can’t stop the timer…

Need some pointers and think it can be done “cleaner” as there are 2 buttons.

#include <LiquidCrystal.h>   //Seriel LCD Here
#include <Wire.h>
#include <LiquidCrystal_I2C.h>
#define ledtimingPin  10
#define ledreadyPin  11
#define ledrunoverPin  12
#define startPin 6
#define stopPin 8
#define resetPin 7

LiquidCrystal_I2C lcd(0x27, 2, 1, 0, 4, 5, 6, 7, 3, POSITIVE);  // Set the LCD I2C address	

int value = LOW;                    // previous value of the LED
int buttonState;                    // variable to store button state
int stateReset;
int lastButtonState;                // variable to store last button state
int blinking;                       // condition for blinking - timer is timing
long interval = 500;                // blink interval - change to suit
long previousMillis = 0;            // variable to store last time LED was updated
long startTime ;                    // start time for stop watch
long elapsedTime ;                  // elapsed time for stop watch
int fractional;                     // variable used to store fractional part of time


void setup()
{
  Serial.begin(9600);

  pinMode(ledtimingPin, OUTPUT);         // sets the digital pin as output
  pinMode(ledreadyPin, OUTPUT);         // sets the digital pin as output
  pinMode(ledrunoverPin, OUTPUT);       // sets the digital pin as output

  pinMode(startPin, INPUT);       // not really necessary, pins default to INPUT anyway
  pinMode(stopPin, INPUT);       // not really necessary, pins default to INPUT anyway
  pinMode(resetPin, INPUT);
  digitalWrite(startPin, HIGH);   // turn on pullup resistors. Wire button so that press shorts pin to ground.
  digitalWrite(stopPin, HIGH);   // turn on pullup resistors. Wire button so that press shorts pin to ground.

  digitalWrite(resetPin, HIGH);

  // set up the LCD's number of columns and rows: 
  lcd.begin(16, 2);
  // Print a message to the LCD.
  lcd.print("--Stop Watch--");
  lcd.setCursor(0, 1);
  lcd.print("System ready!");
  digitalWrite(ledreadyPin, HIGH);
  digitalWrite(ledrunoverPin, LOW);
}

void loop()
{
  // check for button press
  buttonState = digitalRead(startPin);                   // read the button state and store
  buttonState = digitalRead(stopPin);                   // read the button state and store
  stateReset = digitalRead(resetPin);

  if (buttonState == LOW && lastButtonState == HIGH) // check for a high to low transition
  {
    if(!blinking) // like a professional programmer
      // if true then found a new button press while clock is not running - start the clock

      startTime = millis();                                   // store the start time
    blinking = true;                                        // turn on blinking while timing
    delay(5);                                               // short delay to debounce switch
    lastButtonState = buttonState;      // store buttonState in lastButtonState, to compare next time

      lcd.clear();
    lcd.print("--Stop Watch--");
    lcd.setCursor(0, 1);
    lcd.print("Started timing!");
    digitalWrite(ledreadyPin, LOW);

  }

  else if (buttonState == LOW && lastButtonState == HIGH)// check for a high to low transition  //else if or just else???
  {
    if(blinking) // like a professional programmer     
      // if true then found a new button press while clock is running - stop the clock and report

      elapsedTime =   millis() - startTime;              // store elapsed time
    blinking = false;                                  // turn off blinking, all done timing
    lastButtonState = buttonState;                     // store buttonState in lastButtonState, to compare next time

      // routine to report elapsed time
    Serial.print( (int)(elapsedTime / 1000L));         // divide by 1000 to convert to seconds - then cast to an int to print

    Serial.print(".");                             // print decimal point

      // use modulo operator to get fractional part of time
    fractional = (int)(elapsedTime % 1000L);

    // pad in leading zeros - wouldn't it be nice if
    // Arduino language had a flag for this? :)
    if (fractional == 0)
      Serial.print("000");      // add three zero's
    else if (fractional < 10)    // if fractional < 10 the 0 is ignored giving a wrong time, so add the zeros
      Serial.print("00");       // add two zeros
    else if (fractional < 100)
      Serial.print("0");        // add one zero

    Serial.println(fractional);  // print fractional part of time

    // set the cursor to column 0, line 2
    // (note: line 1 is the second row, since counting begins with 0):
    lcd.clear();
    lcd.print("--Stop Watch--");

    lcd.setCursor(0, 0);      
    lcd.print("Run over! time:");

    lcd.setCursor(0, 1);
    lcd.print((int)(elapsedTime / 1000));
    lcd.print(":");

    //lcd.setCursor(10, 1);
    lcd.print(fractional);
    lcd.print(" ms");
    digitalWrite(ledrunoverPin, HIGH);
  }

  else{
    lastButtonState = buttonState;                         // store buttonState in lastButtonState, to compare next time
  }

  if (stateReset == LOW) {
    blinking = false;
    lcd.clear();
    lcd.print("--Stop Watch--");
    lcd.setCursor(0, 1);
    lcd.print("System ready!");
    digitalWrite(ledreadyPin, HIGH);
    digitalWrite(ledrunoverPin, LOW);
  }

  // blink routine - blink the LED while timing
  // check to see if it's time to blink the LED; that is, the difference
  // between the current time and last time we blinked the LED is larger than
  // the interval at which we want to blink the LED.

  if ( (millis() - previousMillis > interval) ) {

    if (blinking == true){
      previousMillis = millis();                         // remember the last time we blinked the LED

      // if the LED is off turn it on and vice-versa.
      if (value == LOW)
        value = HIGH;
      else
        value = LOW;
      digitalWrite(ledtimingPin, value);
    }
    else{
      digitalWrite(ledtimingPin, LOW);                         // turn off LED when not blinking
    }
  }

}

Anyone?

int buttonState;                    // variable to store button state
int stateReset;
int lastButtonState;                // variable to store last button state

Of which switch?

  buttonState = digitalRead(startPin);                   // read the button state and store
  buttonState = digitalRead(stopPin);                   // read the button state and store

In the same variable? It's no wonder the stop pin starts the timer.

I see.

Would for example int button1State; for say start and button2State; for stop be and idea?

Ok, getting there! Got it running pretty much how I want on Lane 1

Now I need to set up Lane 2.

I imagine I need to take the same code for timing and do it for Lane 2 (of course with new pins and buttonState names etc) Not quite sure yet, but i think I might get it.

/* 
SLALOMTIMER V.4
* Based on Paul Badger 2008 - http://playground.arduino.cc/Code/Stopwatch
* Inspiration Alph Mariuz
* Help from Paul S - Arduino forum
*/

#include <LiquidCrystal.h>   //Seriel LCD Here
#include <Wire.h>
#include <LiquidCrystal_I2C.h>
#define ledtimingPin  10
#define ledreadyPin  11
#define ledrunoverPin  12
#define startPin 6
#define stopPin 8
#define resetPin 7

LiquidCrystal_I2C lcd(0x27, 2, 1, 0, 4, 5, 6, 7, 3, POSITIVE);  // Set the LCD I2C address	

int value = LOW;                    // previous value of the LED
int buttonState1;                   // variable to store button state 1
int buttonState2;                   // variable to store button state 2
int lastButtonState1;               // variable to store last button state 1
int lastButtonState2;               // variable to store last button state 2
int stateReset;                     // variable to store reset button state
int blinking;                       // condition for blinking - timer is timing
long interval = 500;                // blink interval - change to suit
long previousMillis = 0;            // variable to store last time LED was updated
long startTime ;                    // start time for stop watch
long elapsedTime ;                  // elapsed time for stop watch
int fractional;                     // variable used to store fractional part of time


void setup()
{
  Serial.begin(9600);

  pinMode(ledtimingPin, OUTPUT);       // sets the digital pin as output
  pinMode(ledreadyPin, OUTPUT);        // sets the digital pin as output
  pinMode(ledrunoverPin, OUTPUT);      // sets the digital pin as output

  pinMode(startPin, INPUT);            // not really necessary, pins default to INPUT anyway
  pinMode(stopPin, INPUT);             // not really necessary, pins default to INPUT anyway
  pinMode(resetPin, INPUT);            // not really necessary, pins default to INPUT anyway
  digitalWrite(startPin, HIGH);        // turn on pullup resistors. Wire button so that press shorts pin to ground.
  digitalWrite(stopPin, HIGH);         // turn on pullup resistors. Wire button so that press shorts pin to ground.

  digitalWrite(resetPin, HIGH);

  // set up the LCD's number of columns and rows: 
  lcd.begin(16, 2);
  // Print a message to the LCD.
  lcd.print("--Slalom Timer--");
  lcd.setCursor(0, 1);
  lcd.print("--Timer ready!--");
  digitalWrite(ledreadyPin, HIGH);
  digitalWrite(ledrunoverPin, LOW);
}

void loop()
{
  // check for button press
  buttonState1 = digitalRead(startPin);                  // read the start button state and store
  buttonState2 = digitalRead(stopPin);                   // read the stop button state and store
  stateReset = digitalRead(resetPin);                    // read the reset button state and store

  if (buttonState1 == LOW && lastButtonState1 == HIGH)   // check for a high to low transition
  {
    if(!blinking) 
      // if true then found a new button press while clock is not running - start the clock

    startTime = millis();                                   // store the start time
    blinking = true;                                        // turn on blinking while timing
    delay(5);                                               // short delay to debounce switch
    lastButtonState1 = buttonState1;                        // store buttonState1 in lastButtonState1, to compare next time

    lcd.clear();
    lcd.print("--Slalom Timer--");
    lcd.setCursor(0, 1);
    lcd.print("Run in progress!");
    digitalWrite(ledreadyPin, LOW);

  }

  else if (buttonState2 == LOW && lastButtonState2 == HIGH)// check for a high to low transition
  {
    if(blinking)      
      // if true then found a new button press while clock is running - stop the clock and report

    elapsedTime =   millis() - startTime;              // store elapsed time
    blinking = false;                                  // turn off blinking, all done timing
    lastButtonState2 = buttonState2;                   // store buttonState2 in lastButtonState, to compare next time

    // routine to report elapsed time
    Serial.print( (int)(elapsedTime / 1000L));         // divide by 1000 to convert to seconds - then cast to an int to print

    Serial.print(".");                             // print decimal point

      // use modulo operator to get fractional part of time
    fractional = (int)(elapsedTime % 1000L);

    // pad in leading zeros - wouldn't it be nice if
    // Arduino language had a flag for this? :)
    if (fractional == 0)
      Serial.print("000");      // add three zero's
    else if (fractional < 10)    // if fractional < 10 the 0 is ignored giving a wrong time, so add the zeros
      Serial.print("00");       // add two zeros
    else if (fractional < 100)
      Serial.print("0");        // add one zero

    Serial.println(fractional);  // print fractional part of time

    // set the cursor to column 0, line 2
    // (note: line 1 is the second row, since counting begins with 0):
    lcd.setCursor(0, 0);  
    lcd.clear();    
    lcd.print("L1:");

    lcd.setCursor(5, 0);
    lcd.print((int)(elapsedTime / 1000));
    lcd.print(":");

    //lcd.setCursor(15, 0);
    lcd.print(fractional);
    lcd.print(" ms");
    
    lcd.setCursor(0, 1);      
    lcd.print("L2:  ---------");  //Not yet implemented. Move and edit  when I figure Lane 2 timing!
    
    
    digitalWrite(ledrunoverPin, HIGH);
  }

  else{
    lastButtonState1 = buttonState1;                         // store buttonState in lastButtonState, to compare next time
    lastButtonState2 = buttonState2;                         // store buttonState in lastButtonState, to compare next time
  }

  if (stateReset == LOW) {
    blinking = false;
    lcd.clear();
    lcd.print("--Slalom Timer--");
    lcd.setCursor(0, 1);
    lcd.print("--Timer ready!--");
    digitalWrite(ledreadyPin, HIGH);
    digitalWrite(ledrunoverPin, LOW);
  }

  // blink routine - blink the LED while timing
  // check to see if it's time to blink the LED; that is, the difference
  // between the current time and last time we blinked the LED is larger than
  // the interval at which we want to blink the LED.

  if ( (millis() - previousMillis > interval) ) 
  {
    if (blinking == true){
      previousMillis = millis();                         // remember the last time we blinked the LED

      // if the LED is off turn it on and vice-versa.
      if (value == LOW)
        value = HIGH;
      else
        value = LOW;
      digitalWrite(ledtimingPin, value);
    }
    else
    {
      digitalWrite(ledtimingPin, LOW);                         // turn off LED when not blinking
    }
  }

}