Coder Social home page Coder Social logo

Comments (10)

speedymk1 avatar speedymk1 commented on July 4, 2024 1

@pedrooct
Hi, I tried it now and I will tell you that everything work for me.
Below you will see how I have it done...

Step 1 -> modify the TFMini.cpp:
delete or comment all Serial.print commands in the TFMini.cpp file.
myone look now like following:

/*
Arduino driver for Benewake TFMini time-of-flight distance sensor.
by Peter Jansen (December 11/2017)
This code is open source software in the public domain.

THIS SOFTWARE IS PROVIDED ''AS IS'' AND ANY
EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
DISCLAIMED. IN NO EVENT SHALL THE AUTHOR(S) BE LIABLE FOR ANY
DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
(INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
(INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS
SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.

The names of the contributors may not be used to endorse or promote products
derived from this software without specific prior written permission.
*/

#include "TFMini.h"

// Constructor
TFMini::TFMini() {
  // Empty constructor
}


boolean TFMini::begin(Stream* _streamPtr) {
  // Store reference to stream/serial object
  streamPtr = _streamPtr;

  // Clear state
  distance = -1;
  strength = -1;
  state = READY;

  // Set standard output mode
  setStandardOutputMode();

  return true;
}


// Public: The main function to measure distance.
uint16_t TFMini::getDistance() {
  int numMeasurementAttempts = 0;
  while (takeMeasurement() != 0) {
    numMeasurementAttempts += 1;
    if (numMeasurementAttempts > TFMINI_MAX_MEASUREMENT_ATTEMPTS) {
//      Serial.println ("TF Mini error: too many measurement attempts");
//      Serial.println ("Last error:");
      if (state == ERROR_SERIAL_NOHEADER)     //Serial.println("ERROR_SERIAL_NOHEADER");
      if (state == ERROR_SERIAL_BADCHECKSUM)  //Serial.println("ERROR_SERIAL_BADCHECKSUM");
      if (state == ERROR_SERIAL_TOOMANYTRIES) //Serial.println("ERROR_SERIAL_TOOMANYTRIES");

      state = ERROR_SERIAL_TOOMANYTRIES;
      distance = -1;
      strength = -1;
      return -1;
    }
  }

  if (state == MEASUREMENT_OK) {
    return distance;
  } else {
    return -1;
  }
}


// Public: Return the most recent signal strength measuremenet from the TF Mini
uint16_t TFMini::getRecentSignalStrength() {
  return strength;
}


// Private: Set the TF Mini into the correct measurement mode
void TFMini::setStandardOutputMode() {
  // Set to "standard" output mode (this is found in the debug documents)
  streamPtr->write((uint8_t)0x42);
  streamPtr->write((uint8_t)0x57);
  streamPtr->write((uint8_t)0x02);
  streamPtr->write((uint8_t)0x00);
  streamPtr->write((uint8_t)0x00);
  streamPtr->write((uint8_t)0x00);
  streamPtr->write((uint8_t)0x01);
  streamPtr->write((uint8_t)0x06);

  delay(100);
}


// Private: Handles the low-level bits of communicating with the TFMini, and detecting some communication errors.
int TFMini::takeMeasurement() {
  int numCharsRead = 0;
  uint8_t lastChar = 0x00;

  // Step 1: Read the serial stream until we see the beginning of the TF Mini header, or we timeout reading too many characters.
  while (1) {

    if (streamPtr->available()) {
      uint8_t curChar = streamPtr->read();

      if ((lastChar == 0x59) && (curChar == 0x59)) {
        // Break to begin frame
        break;

      } else {
        // We have not seen two 0x59's in a row -- store the current character and continue reading.
        lastChar = curChar;
        numCharsRead += 1;
      }
    }

    // Error detection:  If we read more than X characters without finding a frame header, then it's likely there is an issue with
    // the Serial connection, and we should timeout and throw an error.
    if (numCharsRead > TFMINI_MAXBYTESBEFOREHEADER) {
      state = ERROR_SERIAL_NOHEADER;
      distance = -1;
      strength = -1;
      if (TFMINI_DEBUGMODE == 1)// Serial.println("ERROR: no header");
      return -1;
    }

  }

  // Step 2: Read one frame from the TFMini
  uint8_t frame[TFMINI_FRAME_SIZE];

  uint8_t checksum = 0x59 + 0x59;
  for (int i=0; i<TFMINI_FRAME_SIZE; i++) {
    // Read one character
    while (!streamPtr->available()) {
      // wait for a character to become available
    }
    frame[i] = streamPtr->read();

    // Store running checksum
    if (i < TFMINI_FRAME_SIZE-2) {
      checksum += frame[i];
    }
  }

  // Step 2A: Compare checksum
  // Last byte in the frame is an 8-bit checksum
  uint8_t checksumByte = frame[TFMINI_FRAME_SIZE-1];
  if (checksum != checksumByte) {
    state = ERROR_SERIAL_BADCHECKSUM;
    distance = -1;
    strength = -1;
    if (TFMINI_DEBUGMODE == 1)// Serial.println("ERROR: bad checksum");
    return -1;
  }


  // Step 3: Interpret frame
  uint16_t dist = (frame[1] << 8) + frame[0];
  uint16_t st = (frame[3] << 8) + frame[2];
  uint8_t reserved = frame[4];
  uint8_t originalSignalQuality = frame[5];


  // Step 4: Store values
  distance = dist;
  strength = st;
  state = MEASUREMENT_OK;

  // Return success
  return 0;
}

Step 2 -> my testing code:

/* This example shows how to use the TFMini module.
The nodeMCU have an build in Watchdog and therefore it is necessary,
that you delete/disable all <<Serial.print>> commands from the TFMini.cpp.
Otherwise you will run into an restart loop, because the Watchdog become
activated...

Wiring:
TFMini  -> nodeMCU
SDA     -> D2 -> 4 -> Tx
SCL     -> D1 -> 5 -> Rx
VCC     -> 5V
GND     -> GND
*/
#include <Arduino.h>
#include <SoftwareSerial.h>
#include "TFMini.h"

// Setup software serial port
SoftwareSerial mySerial(5, 4);      // connection to TFMini
TFMini         tfmini;              // tfmini access
unsigned long  previousMillis = 0;  // access time
const long interval = 10;           // interval at which to measure (milliseconds)

/*
-----------------S E T U P-----------------
*/
void setup() {
  // Step 1: Initialize hardware serial port (serial debug port)
  Serial.begin(115200);
  // wait for serial port to connect. Needed for native USB port only
  while (!Serial);

  // Step 2: Initialize the data rate for the SoftwareSerial port
  mySerial.begin(TFMINI_BAUDRATE);  // default boudrate is 115200
  delay(10);

  // Step 3: Initialize the TF Mini sensor
  tfmini.begin(&mySerial);
  Serial.println ("Initializing Serial and mySerial finished");
}


/*
-----------------L O O P-----------------
*/
void loop() {
  // we will not use an delay...
  // but we wait some short time before taking the next measurement
  unsigned long currentMillis = millis();
  if (currentMillis - previousMillis >= interval) {
    // save the last measure time
    previousMillis = currentMillis;
    // Take one TF Mini distance measurement
    uint16_t dist = tfmini.getDistance();
    uint16_t strength = tfmini.getRecentSignalStrength();
    // Display the measurement
    Serial.print(dist);
    Serial.print(" cm   Signal: ");
    Serial.println(strength);
  }
}

from tfmini.

speedymk1 avatar speedymk1 commented on July 4, 2024 1

Yes, it work how it should.
Perfect, thanks again 👌😊

from tfmini.

sachinELEVEN avatar sachinELEVEN commented on July 4, 2024 1

@pedrooct
Hi, I tried it now and I will tell you that everything work for me.
Below you will see how I have it done...

Step 1 -> modify the TFMini.cpp:
delete or comment all Serial.print commands in the TFMini.cpp file.
myone look now like following:

/*
Arduino driver for Benewake TFMini time-of-flight distance sensor.
by Peter Jansen (December 11/2017)
This code is open source software in the public domain.

THIS SOFTWARE IS PROVIDED ''AS IS'' AND ANY
EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
DISCLAIMED. IN NO EVENT SHALL THE AUTHOR(S) BE LIABLE FOR ANY
DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
(INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
(INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS
SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.

The names of the contributors may not be used to endorse or promote products
derived from this software without specific prior written permission.
*/

#include "TFMini.h"

// Constructor
TFMini::TFMini() {
  // Empty constructor
}


boolean TFMini::begin(Stream* _streamPtr) {
  // Store reference to stream/serial object
  streamPtr = _streamPtr;

  // Clear state
  distance = -1;
  strength = -1;
  state = READY;

  // Set standard output mode
  setStandardOutputMode();

  return true;
}


// Public: The main function to measure distance.
uint16_t TFMini::getDistance() {
  int numMeasurementAttempts = 0;
  while (takeMeasurement() != 0) {
    numMeasurementAttempts += 1;
    if (numMeasurementAttempts > TFMINI_MAX_MEASUREMENT_ATTEMPTS) {
//      Serial.println ("TF Mini error: too many measurement attempts");
//      Serial.println ("Last error:");
      if (state == ERROR_SERIAL_NOHEADER)     //Serial.println("ERROR_SERIAL_NOHEADER");
      if (state == ERROR_SERIAL_BADCHECKSUM)  //Serial.println("ERROR_SERIAL_BADCHECKSUM");
      if (state == ERROR_SERIAL_TOOMANYTRIES) //Serial.println("ERROR_SERIAL_TOOMANYTRIES");

      state = ERROR_SERIAL_TOOMANYTRIES;
      distance = -1;
      strength = -1;
      return -1;
    }
  }

  if (state == MEASUREMENT_OK) {
    return distance;
  } else {
    return -1;
  }
}


// Public: Return the most recent signal strength measuremenet from the TF Mini
uint16_t TFMini::getRecentSignalStrength() {
  return strength;
}


// Private: Set the TF Mini into the correct measurement mode
void TFMini::setStandardOutputMode() {
  // Set to "standard" output mode (this is found in the debug documents)
  streamPtr->write((uint8_t)0x42);
  streamPtr->write((uint8_t)0x57);
  streamPtr->write((uint8_t)0x02);
  streamPtr->write((uint8_t)0x00);
  streamPtr->write((uint8_t)0x00);
  streamPtr->write((uint8_t)0x00);
  streamPtr->write((uint8_t)0x01);
  streamPtr->write((uint8_t)0x06);

  delay(100);
}


// Private: Handles the low-level bits of communicating with the TFMini, and detecting some communication errors.
int TFMini::takeMeasurement() {
  int numCharsRead = 0;
  uint8_t lastChar = 0x00;

  // Step 1: Read the serial stream until we see the beginning of the TF Mini header, or we timeout reading too many characters.
  while (1) {

    if (streamPtr->available()) {
      uint8_t curChar = streamPtr->read();

      if ((lastChar == 0x59) && (curChar == 0x59)) {
        // Break to begin frame
        break;

      } else {
        // We have not seen two 0x59's in a row -- store the current character and continue reading.
        lastChar = curChar;
        numCharsRead += 1;
      }
    }

    // Error detection:  If we read more than X characters without finding a frame header, then it's likely there is an issue with
    // the Serial connection, and we should timeout and throw an error.
    if (numCharsRead > TFMINI_MAXBYTESBEFOREHEADER) {
      state = ERROR_SERIAL_NOHEADER;
      distance = -1;
      strength = -1;
      if (TFMINI_DEBUGMODE == 1)// Serial.println("ERROR: no header");
      return -1;
    }

  }

  // Step 2: Read one frame from the TFMini
  uint8_t frame[TFMINI_FRAME_SIZE];

  uint8_t checksum = 0x59 + 0x59;
  for (int i=0; i<TFMINI_FRAME_SIZE; i++) {
    // Read one character
    while (!streamPtr->available()) {
      // wait for a character to become available
    }
    frame[i] = streamPtr->read();

    // Store running checksum
    if (i < TFMINI_FRAME_SIZE-2) {
      checksum += frame[i];
    }
  }

  // Step 2A: Compare checksum
  // Last byte in the frame is an 8-bit checksum
  uint8_t checksumByte = frame[TFMINI_FRAME_SIZE-1];
  if (checksum != checksumByte) {
    state = ERROR_SERIAL_BADCHECKSUM;
    distance = -1;
    strength = -1;
    if (TFMINI_DEBUGMODE == 1)// Serial.println("ERROR: bad checksum");
    return -1;
  }


  // Step 3: Interpret frame
  uint16_t dist = (frame[1] << 8) + frame[0];
  uint16_t st = (frame[3] << 8) + frame[2];
  uint8_t reserved = frame[4];
  uint8_t originalSignalQuality = frame[5];


  // Step 4: Store values
  distance = dist;
  strength = st;
  state = MEASUREMENT_OK;

  // Return success
  return 0;
}

Step 2 -> my testing code:

/* This example shows how to use the TFMini module.
The nodeMCU have an build in Watchdog and therefore it is necessary,
that you delete/disable all <<Serial.print>> commands from the TFMini.cpp.
Otherwise you will run into an restart loop, because the Watchdog become
activated...

Wiring:
TFMini  -> nodeMCU
SDA     -> D2 -> 4 -> Tx
SCL     -> D1 -> 5 -> Rx
VCC     -> 5V
GND     -> GND
*/
#include <Arduino.h>
#include <SoftwareSerial.h>
#include "TFMini.h"

// Setup software serial port
SoftwareSerial mySerial(5, 4);      // connection to TFMini
TFMini         tfmini;              // tfmini access
unsigned long  previousMillis = 0;  // access time
const long interval = 10;           // interval at which to measure (milliseconds)

/*
-----------------S E T U P-----------------
*/
void setup() {
  // Step 1: Initialize hardware serial port (serial debug port)
  Serial.begin(115200);
  // wait for serial port to connect. Needed for native USB port only
  while (!Serial);

  // Step 2: Initialize the data rate for the SoftwareSerial port
  mySerial.begin(TFMINI_BAUDRATE);  // default boudrate is 115200
  delay(10);

  // Step 3: Initialize the TF Mini sensor
  tfmini.begin(&mySerial);
  Serial.println ("Initializing Serial and mySerial finished");
}


/*
-----------------L O O P-----------------
*/
void loop() {
  // we will not use an delay...
  // but we wait some short time before taking the next measurement
  unsigned long currentMillis = millis();
  if (currentMillis - previousMillis >= interval) {
    // save the last measure time
    previousMillis = currentMillis;
    // Take one TF Mini distance measurement
    uint16_t dist = tfmini.getDistance();
    uint16_t strength = tfmini.getRecentSignalStrength();
    // Display the measurement
    Serial.print(dist);
    Serial.print(" cm   Signal: ");
    Serial.println(strength);
  }
}

Amazing and thank you for your solution 😀 . Also FYI this solution works even for TF-LUNA LIDAR

from tfmini.

jucall avatar jucall commented on July 4, 2024

You are wright. I tried to use TFMini with Wemos Mini Pro D (with ESP8266 Core Processor), At the begining worked OK, but suddenly appears that message.

TF Mini error: too many measurement attempts
Last error:
ERROR_SERIAL_NOHEADER
65535 cm sigstr: 65535

Do you know what can I do?, Do you have a code to reset o do something to fix it?. It's hard to believe that software issue could damage forever the sensor.

This problem doesn't happend with Arduinos?.

Can you share please a zip file with your example project and corrected serial communications libraries to use TFMini with ESP boards (like Wemos)?. The other solutions is have to use an Arduino Pro Mini working at 3.3 Volts to communicate with TFMini.

Greetings.
JC

from tfmini.

pedrooct avatar pedrooct commented on July 4, 2024

HI @jucall , can you provide your code please , i'm also trying to use this lidar but to no success . Thank you.

from tfmini.

speedymk1 avatar speedymk1 commented on July 4, 2024

Is there a solution to use TFMini with NodeMCU 12E ?

from tfmini.

pedrooct avatar pedrooct commented on July 4, 2024

@speedymk1 Hello,I don't have the code but from what i remember you need to delete all the serial.print and serial println from tfmini.cpp.

That should do the trick. If it did please confirm this. Thank you.

from tfmini.

pedrooct avatar pedrooct commented on July 4, 2024

@speedymk1 so it work right ?

from tfmini.

HuanLiangTsai avatar HuanLiangTsai commented on July 4, 2024

I followed the above two steps and code. However, I got the following message. How can I solve the problem? Many thanks.

TF Mini error: too many measurement attempts
Last error:
ERROR_SERIAL_BADCHECKSUM
65535 cm Signal: 65535

from tfmini.

HuanLiangTsai avatar HuanLiangTsai commented on July 4, 2024

Finally the results showing "65535 cm Signal: 65535" were not correct, I am sincerely asking possible help. Many thanks.

from tfmini.

Related Issues (12)

Recommend Projects

  • React photo React

    A declarative, efficient, and flexible JavaScript library for building user interfaces.

  • Vue.js photo Vue.js

    🖖 Vue.js is a progressive, incrementally-adoptable JavaScript framework for building UI on the web.

  • Typescript photo Typescript

    TypeScript is a superset of JavaScript that compiles to clean JavaScript output.

  • TensorFlow photo TensorFlow

    An Open Source Machine Learning Framework for Everyone

  • Django photo Django

    The Web framework for perfectionists with deadlines.

  • D3 photo D3

    Bring data to life with SVG, Canvas and HTML. 📊📈🎉

Recommend Topics

  • javascript

    JavaScript (JS) is a lightweight interpreted programming language with first-class functions.

  • web

    Some thing interesting about web. New door for the world.

  • server

    A server is a program made to process requests and deliver data to clients.

  • Machine learning

    Machine learning is a way of modeling and interpreting data that allows a piece of software to respond intelligently.

  • Game

    Some thing interesting about game, make everyone happy.

Recommend Org

  • Facebook photo Facebook

    We are working to build community through open source technology. NB: members must have two-factor auth.

  • Microsoft photo Microsoft

    Open source projects and samples from Microsoft.

  • Google photo Google

    Google ❤️ Open Source for everyone.

  • D3 photo D3

    Data-Driven Documents codes.