Reading the OBDH bus in a car

Since some time I have an idea concerning reading the data bus in the car for RPM, speed, gear and maybe some more. The first thought is building the project on an UNO as I have a number of them. A few alarms, beep, beep sound, when passing 2000, 3000 and 4000 RPM. The silent engine doesn't tip me for gear shifts but the alarms will do it.

This interface is shipped out, sales site link: Freematics OBD-II UART Adapter V2.1 (for Arduino). Link: Freematics OBD-II UART Adapter V2.1 (for Arduino)

I found a link to a number of different libraries:
GitHub - stanleyhuangyc/ArduinoOBD: OBD-II library and sketches for Arduino

Does any helper/member have experience of this device and those libraries? My whish is a tip for a useful library and hopefully not downloading the lot and testing.

For what car model and year do you plan to do this?

It's a Skoda Fabia Combi 2018, bought June 2022.

Being so new, I would assume it is compatible with standard OBD protocols, so a good start would be the example on the sales page you posted, which conveniently is also an indicator for engine RPM above a threshold.

Unfortunately with reading vehicle diagnostics sometimes testing and experimenting is still needed, but all things considered your car should comply with the standards so it might just be as simple as grabbing the first example code you see and having it just work.

Simple example code I used the first time experiencing the NEO6-M GPS and built my code around it.

I have more to explore on the sales site. What did You click on to find what You found?

Just scrolled down to the heading "Arduino Library" in the item description

I have used the Freematics with their library.

https://freematics.com/products/freematics-obd-ii-uart-adapter-mk2/

is what I used.

#include <U8g2lib.h>
#include "freeRTOSSTUFF.h"
#include <OBD2UART.h>
////
//const int SerialDataBits = 115200;
const int DisplayK = 100000;
/////////////////////////////////////////////////////////////////////////////////////////////
void setup()
{
  //  //// CORE 0
  xTaskCreatePinnedToCore ( fUpdateDisplay, "fUpdateDisplay", DisplayK, NULL, Priority4, NULL, TaskCore0 ); // assigned to core
}
////
void loop() {}
////
/////////////////////////////////////////////////////
void fUpdateDisplay( void * parameter )
{
  U8G2_SSD1309_128X64_NONAME0_F_4W_HW_SPI u8g2(U8G2_R0, /* cs=*/ 5, /* dc=*/ 2, /* reset=*/ 4);
  COBD obd;
  byte version = obd.begin();
  log_i("Freematics OBD-II Adapter %d", version);

  if ( u8g2.begin() )
  {
    log_i( "u8gx.begin() all OK" );
  }
  int xValIncrement = 10;
  int Xval = 0;
  int Val;
  String temp = "";
  temp.reserve(200);
  u8g2.setFont(u8g2_font_ncenB08_tr); // choose a suitable font
  for (;;)
  {
    u8g2.clearBuffer(); // clear the internal memory
    ////
    temp.concat( "Batt: " );
    temp.concat( String(obd.getVoltage()) );
    temp.concat( "V " );
    // PID_FUEL_LEVEL
    temp.concat( " Fuel: ");
    obd.readPID( PID_FUEL_LEVEL, Val);
    temp.concat( String(Val) );
    temp.concat( "%" );
    u8g2.setCursor( 0, Xval ); u8g2.print( temp ); // do not 0 Val, used below // send the bat and fuel to the oled
    temp = "";
    // DISPLAY FUEL LEVEL BAR
    u8g2.drawHLine( 0, 15, 100); // top
    int Y = 17;
    for ( int x = 0; x <= Val; x++)
    {
      u8g2.drawVLine( x, Y, 3);
      log_i( "X %d, Y %d", x, Y );
    }
    u8g2.drawVLine( 25, 14, 8); // 25%
    u8g2.drawVLine( 50, 14, 8); // 50%
    u8g2.drawVLine( 75, 14, 8); // 75 percent
    u8g2.drawVLine( 100, 14, 8); //  100%
    u8g2.drawHLine( 0, 21, 100);
    Val = 0;
    //PID_RPM
    Xval = 43;
    obd.readPID( PID_RPM, Val );
    /*/ 100 pixels for 5000 rmp = 50 pixel per 1000 rpm
    */
    int rpm = Val / 50;
    Y = 27;
    for ( int x = 0; x <= rpm; x++)
    {
      u8g2.drawVLine( x, Y, 5);
    }
    u8g2.drawVLine( 50, Xval + 2, 8); // 25%
    temp.concat( String( Val) );
    temp.concat( " RPM's " );
    u8g2.setCursor( 25, Xval ); u8g2.print( temp ); Val = 0;
    temp = "" ;
    // PID_COOLANT_TEMP
    Xval = Xval + xValIncrement;
    temp.concat( "Coolant: " );
    obd.readPID( PID_COOLANT_TEMP, Val);
    temp.concat( String(Val) );
    temp.concat( "C / ");
    temp.concat( String( ((float)Val * 1.8f) + 32.0f) );
    temp.concat( " F");
    u8g2.setCursor( 0, Xval ); u8g2.print( temp ); Val = 0;
    temp = "";
    //    // PID_SPEED
    //    Xval = Xval + xValIncrement;
    // u8g2.drawStr( 0, Xval, "Speed: " );
    // Xval = Xval + xValIncrement;
    //    u8g2.setFont( u8g2_font_osb41_tf ); // choose a suitable font
    //    obd.readPID( PID_SPEED, Val);
    //    float mph = (float)Val * .62137119f;
    //    u8g2.setCursor( 0, 50 ); u8g2.print( int(mph) );
    //
    u8g2.sendBuffer();          // transfer internal memory to the display
    //        // Serial.print(uxTaskGetStackHighWaterMark( NULL ));
    //        // Serial.println();
    //        // Serial.flush();
    //        // vTaskDelay(7);
    Xval = xValIncrement; // reset  Xval for the next loop.
    Val = 0; // set value to 0 for next loop
    vTaskDelay( 500 );
  }
  vTaskDelete( NULL );
} // void fUpdateDisplay( void * parameter )
////
//////////////////////////////////////////////////////

That's the page I've been looking at, and posted a link to. Didn't notice things like example code. Looking again.

Thanks. I'll look it up. Haven't got the OBDH circuit yet but I'll take a serious look into Your link.

example code.

Thanks!
I have work to do.
The dream is calling a can bus reader like the GPS.update, GPS.encode, and then pick the data I want like gps.speed, gps.altitude etc.
I'll see what I find.

Oh, get the 90 degree ODBCII connector for the freematics. For me the freematics with the 90 degree ODBC conector lays flat against the cars components instead of sticking out where your knee can hit it. Also, consider the ribbon connector extension so that the project can be tucked away when development is done.

look in the.h files for PID's

Thanks again. I haven't yet looked up where the connector is sitting.
The knee knocking things has already happend. The lights are turned on when leaving the car......

That tip is gold. Haven't been thinking about were to put the controller and the beeper.

Thanks again.

Just saved the browser link to this forum page. It's a gold mine.

1 Like

I've paid the duties so the device is close. Clicking the link "master/libraries/OBD2UART" I get a list of files. How do I proceed to get them accepted in the Arduino library? Copy and paste files "just like that" doesn't work as I've got it.
Can You please provide the next step?

On this page

is a green drop down button that reads "CODE". Press the button and download the zip. Then use the IDE to install library from zip file.

Thanks! I'll try that when being back to the Pc.

Done but.....
Copied the downloaded folder into arduino/library/
Running the IDE librarian I don't find any OBDH stuff.

Installing new libraries happens so seldom and every time it gets difficult.
Posting a screenshot of the file I hope I got:

You did Sketch|Include Library|Add .Zip Library and that did not install the downloaded zip file as a library into the Arduino IDE?

Gave the questions a second punch, unzipped an Arduino_OBDH_master something... but wonder if I got the right stuff. The Freematics device reads the CAN bus. Then it communicates using UART/Serial, as I got it. I got a question about installing all or only OBDH. Selected all.

Intend to search for example code and see what it looks like.

Your MCU communicates with the Freematics via serial.

I bought a whole bunch of these adapters for a project, but ultimately abandoned the project as I could only read one value from the adapter a second. Reading 10 or so readings from it took a long time. Hope you have better luck.