0

I found a really nice 24 bit I2C adc which was fairly cheap as well (ADS1219) but as far as I could tell there are no libraries for it so I decided to make my own. I have managed to write functions and get everything working on the arduino itself but I've been having massive issues with converting it into a library. So I tried a very basic sketch to see if I can do something as simple as printing hello world using the library. Here is my ADS1219.h file:

#ifndef ADS1219
#define ADS1219

#if ARDUINO >= 100
 #include "Arduino.h"
#else
 #include "WProgram.h"
#endif

class ADS1219{
public:
 ADS1219();
 void begin();
 void printHello();
};

#endif

And the ADS1219.cpp:

#if ARDUINO >= 100
 #include "Arduino.h"
#else
 #include "WProgram.h"
#endif

#include 

ADS1219::ADS1219{
 Serial.println("New object created!");
}

void ADS1219::begin(){
 Serial.begin(9600);
}

void ADS1219::printHello(){
 Serial.println("Hello World");
}

and my main sketch:

#include 

ads = new ADS1219;

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

void loop() {
  ads.printHello();
  delay(2000);
}

but I get this really long error which basically says I've failed with creating the ads object. I tried ADS1219 ads; as well but same error ... not sure what's wrong tbh.

Arduino: 1.8.8 (Windows 10), Board: "Arduino Nano, ATmega328P (Old Bootloader)"

In file included from sketchADS1219.cpp:7:0:

ADS1219.h:14:11: error: expected unqualified-id before ')' token

   ADS1219();

           ^

ADS1219.h:12:14: error: an anonymous struct cannot have function members

 class ADS1219{

              ^

ADS1219.h:18:1: error: abstract declarator '' used as declaration

 };

 ^

ADS1219.cpp:9:17: error: expected id-expression before '{' token

 ADS1219::ADS1219{

                 ^

ADS1219.cpp:13:21: error: explicit qualification in declaration of 'void begin()'

 void ADS1219::begin(){

                     ^

ADS1219.cpp:17:26: error: explicit qualification in declaration of 'void printHello()'

 void ADS1219::printHello(){

                          ^

In file included from C:UsersOM222ODesktopadslibadslib.ino:1:0:

ADS1219.h:14:11: error: expected unqualified-id before ')' token

   ADS1219();

           ^

ADS1219.h:12:14: error: an anonymous struct cannot have function members

 class ADS1219{

              ^

ADS1219.h:18:1: error: abstract declarator '' used as declaration

 };

 ^

adslib:3:1: error: 'ads' does not name a type

 ads = new ADS1219;

 ^

C:UsersOM222ODesktopadslibadslib.ino: In function 'void setup()':

adslib:7:3: error: 'ads' was not declared in this scope

   ads.begin();

   ^

C:UsersOM222ODesktopadslibadslib.ino: In function 'void loop()':

adslib:11:3: error: 'ads' was not declared in this scope

   ads.printHello();

   ^

exit status 1
expected unqualified-id before ')' token

This report would have more information with
"Show verbose output during compilation"
option enabled in File -> Preferences.
9
  • Sorry I didn't know that existed ... there are so many different SEs hahaha. I'll move it to there.
    – OM222O
    Dec 26, 2018 at 23:22
  • First error is "#define ADS1219". Use the convention "#define ADS1219_H" instead. Please come back for more C++ help :). Dec 26, 2018 at 23:40
  • That changed absolutely nothing :D
    – OM222O
    Dec 26, 2018 at 23:43
  • I even tried downloading the exact code some poeple showed to create libraries but I still had no luck! literally the exact same code doesn't wanna work on my machine! Any ideas on what I might be doing wrong? edit: here is the link which I followed: alanzucconi.com/2016/05/11/libraries-for-arduino
    – OM222O
    Dec 27, 2018 at 0:10
  • 1
    You don't have to check for an old arduino version. That is no longer used. It is almost 2019. Just include the Arduino.h (only in the file ADS1219.h). What is a #include without specifying which file to include? In the sketch a ads ADS1219; is enough. Github is full of arduino libraries, you can find many examples there, for example: github.com/Locoduino/SlowMotionServo/tree/master/src and github.com/winlinvip/SimpleDHT (just two random chosen libraries, there must be hundreds of them).
    – Jot
    Dec 27, 2018 at 0:26

3 Answers 3

2

Your problem stems from this line:

#define ADS1219

You define the macro ADS1219 as empty. From that point on all references to ADS1219 get replaced with nothing. For example:

class ADS1219{
public:
 ADS1219();
 void begin();
 void printHello();
};

becomes:

class {
public:
 ();
 void begin();
 void printHello();
};

And

void ADS1219::begin(){
 Serial.begin(9600);
}

becomes:

void ::begin(){
 Serial.begin(9600);
}

By using the same name in your header guard as your class name you screw everything else up.

I always use strict rules for header guard macros to ensure that they never conflict with anything else. You should change yours to read something else. I would use:

#ifndef _ADS1219_H
#define _ADS1219_H

// ... content

#endif

You are also lacking the parenthesis in the constructor implementation:

ADS1219::ADS1219{
 Serial.println("New object created!");
}

should read:

ADS1219::ADS1219(){
 Serial.println("New object created!");
}

And you don't give your ads variable a type and you don't want to use new:

ads = new ADS1219;

should read:

ADS1219 ads;
3
  • Also in the cpp file he should not include again the Arduino.h file, but rather include only the library file (ADS1219.h). Moreover, in my libraries I stopped including WProgram.h. Do you think it is still required?
    – frarugi87
    Dec 27, 2018 at 10:25
  • I haven't included wprogram.h for ages. It doesn't hurt to include a file multiple times as headers should include header guards.
    – Majenko
    Dec 27, 2018 at 10:34
  • thanks this has fixed my issue for now :D I will try to finis the rest on my own but I still might need some help.I'll publish it as soon as I finished
    – OM222O
    Dec 27, 2018 at 12:28
1

Are you sure you're compiling this for C++ and not C?

In any case, you're defining

#define ADS1219

I'm not sure what that does to your class name. Have you tried to

#define ADS1219_H  // <- Standard include guard

instead? Does this yield different results.

5
  • arduino is C itself but the file extension is cpp (c plus plus) so I'm a bit confused myself. Changing it to ADS1219_H yields the same error message.
    – OM222O
    Dec 26, 2018 at 21:35
  • Considering that the class keyword only makes sense in a C++ environment it should be C++ and the compiler should be configured as such. To me, this looks like you're already doing that in the Arduino IDE so it should be configured correctly. Unfortunately I'm out of luck here. Just one sidenote (not related to your issue): You're missing the parantheses on the line where you instantiate your object (the one with the new keyword)
    – Tom L.
    Dec 26, 2018 at 21:48
  • thanks for pointing that out and yes, I am using the IDE. I'm pretty sure it uses GCC linker and is already configured correctly.
    – OM222O
    Dec 26, 2018 at 22:02
  • Standard include guard - isnt' that what #pragma once is used for? Dec 27, 2018 at 3:23
  • 1
    Arduino is c++ not c.
    – Majenko
    Dec 27, 2018 at 10:35
0

I have made a lot of progress and almost everything works fine ... except I initially used strings in switch case for setting up the voltage reference and conversion modes ... it did not like it at all. I instead aimed to use enums for the same purpose but I'm getting this error now:

Arduino: 1.8.8 (Windows 10), Board: "Arduino Nano, ATmega328P (Old Bootloader)"

In file included from sketch\LibraryExample1.ino.cpp:1:0:

C:\Program Files (x86)\Arduino\hardware\arduino\avr\cores\arduino/Arduino.h:81:18: error: expected identifier before numeric constant

 #define INTERNAL 3

                  ^

C:\Users\OM222O\Documents\Arduino\libraries\ADS1219/ADS1219.h:49:3: note: in expansion of macro 'INTERNAL'

   INTERNAL = VREF_INTERNAL,

   ^

C:\Program Files (x86)\Arduino\hardware\arduino\avr\cores\arduino/Arduino.h:81:18: error: expected '}' before numeric constant

 #define INTERNAL 3

                  ^

C:\Users\OM222O\Documents\Arduino\libraries\ADS1219/ADS1219.h:49:3: note: in expansion of macro 'INTERNAL'

   INTERNAL = VREF_INTERNAL,

   ^

C:\Program Files (x86)\Arduino\hardware\arduino\avr\cores\arduino/Arduino.h:81:18: error: expected unqualified-id before numeric constant

 #define INTERNAL 3

                  ^

C:\Users\OM222O\Documents\Arduino\libraries\ADS1219/ADS1219.h:49:3: note: in expansion of macro 'INTERNAL'

   INTERNAL = VREF_INTERNAL,

   ^

In file included from C:\Users\OM222O\Desktop\LibraryExample1\LibraryExample1.ino:2:0:

C:\Users\OM222O\Documents\Arduino\libraries\ADS1219/ADS1219.h:51:1: error: expected declaration before '}' token

 }adsRef_t;

 ^

exit status 1
Error compiling for board Arduino Nano.

This report would have more information with
"Show verbose output during compilation"
option enabled in File -> Preferences.

my ADS1219.h file is:

#ifndef ADS1219_H
#define ADS1219_H

#if (ARDUINO >=100)
  #include "Arduino.h"
#else
  #include "WProgram.h"
#endif

#include <Wire.h>

#define CONFIG_REGISTER_ADDRESS 0x20
#define STATUS_REGISTER_ADDRESS 0x24

#define MUX_MASK                0x1F
#define MUX_DIFF_0_1            0x00
#define MUX_DIFF_2_3            0x20
#define MUX_DIFF_1_2            0x40
#define MUX_SINGLE_0            0x60
#define MUX_SINGLE_1            0x80
#define MUX_SINGLE_2            0xA0
#define MUX_SINGLE_3            0xC0
#define MUX_SHORTED             0xE0

#define GAIN_MASK               0xEF
#define GAIN_ONE                0x00
#define GAIN_FOUR               0x10

#define DATA_RATE_MASK          0xF3
#define DATA_RATE_20            0x00
#define DATA_RATE_90            0x04
#define DATA_RATE_330           0x08
#define DATA_RATE_1000          0x0c

#define MODE_MASK               0xFD
#define MODE_SINGLE_SHOT        0x00
#define MODE_CONTINUOUS         0x02

#define VREF_MASK               0xFE
#define VREF_INTERNAL           0x00
#define VREF_EXTERNAL           0x01

typedef enum{
  ONE   = GAIN_ONE,
  FOUR  = GAIN_FOUR
}adsGain_t;

typedef enum{
  INTERNAL  = VREF_INTERNAL,
  EXTERNAL  = VREF_EXTERNAL
}adsRef_t;

typedef enum{
  SINGLE_SHOT   = MODE_SINGLE_SHOT,
  CONTINUOUS    = MODE_CONTINUOUS
}adsMode_t;

class ADS1219  {
  protected:
    uint8_t address;
  public:
    // Constructor 
    ADS1219(int drdy, uint8_t addr = 0x40);

    // Methods
    void begin();
    void resetConfig();
    long readSingleEnded(int channel);
    long readDifferential_0_1();
    long readDifferential_2_3();
    long readDifferential_1_2();
    long readShorted();
    void setGain(adsGain_t gain);
    void setDataRate(int rate);
    void setConversionMode(adsMode_t mode);
    void setVoltageReference(adsRef_t vref);

  private:
    void writeRegister(uint8_t data);
    uint8_t readRegister(uint8_t reg);
    long readConversionResult();
    uint8_t config;
    int data_ready;
};
#endif

and my cpp file is:

#if ARDUINO >= 100
 #include "Arduino.h"
#else
 #include "WProgram.h"
#endif

#include <Wire.h>
#include "ADS1219.h"

static uint8_t i2cRead(void) {
  #if ARDUINO >= 100
  return Wire.read();
  #else
  return Wire.receive();
  #endif
}

static void i2cWrite(uint8_t x) {
  #if ARDUINO >= 100
  Wire.write(x);
  #else
  Wire.send(x);
  #endif
}


ADS1219::ADS1219(int drdy, uint8_t addr) {
  data_ready = drdy;
  address = addr;
  config = 0x00;
}

void ADS1219::begin() {
  Wire.begin();
}

uint8_t ADS1219::readRegister(uint8_t reg){
  Wire.beginTransmission(address);
  i2cWrite(reg);
  Wire.endTransmission();
  Wire.requestFrom((uint8_t)address,(uint8_t)1);
  return i2cRead();
}

void ADS1219::writeRegister(uint8_t data){
  Wire.beginTransmission(address);
  i2cWrite(CONFIG_REGISTER_ADDRESS);
  i2cWrite(data);
  Wire.endTransmission();
}

long ADS1219::readConversionResult(){
  Wire.beginTransmission(address);
  i2cWrite(0x10);
  Wire.endTransmission();
  Wire.requestFrom((uint8_t)address,(uint8_t)3);
  byte dataMSB = i2cRead();
  byte data = i2cRead();
  byte dataLSB = i2cRead();
  long data32 = dataMSB;
  data32 <<= 8;
  data32 |= data;
  data32 <<= 8;
  data32 |= dataLSB;
  return (data32 << 8) >> 8;
}

void ADS1219::resetConfig(){
    writeRegister(0x00);
}

long ADS1219::readSingleEnded(int channel){
    if (channel > 3) return 0;
    config &= MUX_MASK;
    switch (channel){
    case (0):
      config |= MUX_SINGLE_0;
      break;
    case (1):
      config |= MUX_SINGLE_1;
      break;
    case (2):
      config |= MUX_SINGLE_2;
      break;
    case (3):
      config |= MUX_SINGLE_3;
      break;
    default:
      break;
  }
  writeRegister(config);
  while(digitalRead(data_ready)==1);
  return readConversionResult();
}

long ADS1219::readDifferential_0_1(){
  config &= MUX_MASK;
  config |= MUX_DIFF_0_1;
  writeRegister(config);
  while(digitalRead(data_ready)==1);
  return readConversionResult();
}

long ADS1219::readDifferential_2_3(){
  config &= MUX_MASK;
  config |= MUX_DIFF_2_3;
  writeRegister(config);
  while(digitalRead(data_ready)==1);
  return readConversionResult();
}

long ADS1219::readDifferential_1_2(){
  config &= MUX_MASK;
  config |= MUX_DIFF_1_2;
  writeRegister(config);
  while(digitalRead(data_ready)==1);
  return readConversionResult();
}

long ADS1219::readShorted(){
  config &= MUX_MASK;
  config |= MUX_SHORTED;
  writeRegister(config);
  while(digitalRead(data_ready)==1);
  return readConversionResult();
}

void ADS1219::setGain(adsGain_t gain){
    config &= GAIN_MASK;
    config |= gain;
  writeRegister(config);
}

void ADS1219::setDataRate(int rate){
    config &= DATA_RATE_MASK;
    switch (rate){
    case (20):
      config |= DATA_RATE_20;
      break;
    case (90):
      config |= DATA_RATE_90;
      break;
    case (330):
      config |= DATA_RATE_330;
      break;
    case (1000):
      config |= DATA_RATE_1000;
      break;
    default:
      break;
  }
  writeRegister(config);
}

void ADS1219::setConversionMode(adsMode_t mode){
    config &= MODE_MASK;
    config |= mode;
  writeRegister(config);
}

void ADS1219::setVoltageReference(adsRef_t vref){
    config &= VREF_MASK;
    config |= vref;
  writeRegister(config);
}

it seems to be passing Gain (or maybe hasn't compiled that yet) but failing on the reference selection ... I don't know what I should change in order to fix the issue.

Edit: I'm really hoping it's not another naming convention thing ... if it is, I'm sorry but C++ seems to waaaaayyyy too picky about names in general

3

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge that you have read and understand our privacy policy and code of conduct.

Not the answer you're looking for? Browse other questions tagged or ask your own question.