I am trying to create a way in this library, to be able to pass an option in the library's instantiation using simple terms. And instead of using a primitive data type, I want to use an enum which in this situation would be a perfect option.
I created a model library for simplicity to show what it is i am TRYING to do. I use CLion as my IDE and it doesn't seem to have a problem with what I'm doing, but when I compile the sketch, the compiler throws an error:
error: expected primary-expression before '.'
and it references the macro declaration.
Anyways, here is the example library:
header:
#ifndef Library_h
#define Library_h
#define OPTION1 options.O1
#define OPTION2 options.O2
#define OPTION3 options.O3
class Library {
enum options {
O1, O2, O3
};
public:
Library(unsigned long time, char color);
Library(unsigned long time, char color, options option);
private:
unsigned long timeValue = 0;
char mainColor;
options userOption;
};
#endif
code:
#include "library.h"
Library::Library(unsigned long time, char color) {
timeValue = time;
mainColor = color;
}
Library::Library(unsigned long time, char color, options option) {
timeValue = time;
mainColor = color;
userOption = option;
}
If the enum is defined in the class header, you can use it the way you describe, in the primary sketch. Or in the class, and using the scope resolution operator, as in reply #4.
Not sure what you mean exactly by name collisions, but if you're referring to the name of the macro itself, I suppose it could happen if the user of the library was using another library with the same macro name ... but that would be an issue whether or not I assigned an enum value to the macro or not, right?
Or are you referring to the name of the enum as a possible 'name collision'?
If the user or another library have a variable/function/macro/whatever, named OPTION1, in most cases there will be an error. For example if the user declare a variable int OPTION1 = 123; after including your library, then that name will be replaced by the content of your macro, it will become int options::O1 = 123; which is not good
But if you use
class Library {
public :
enum options {
OPTION1, OPTION2, OPTION3
};
...
}
...
Library go(1000, 8, Library::OPTION1);
I didn't see in the example you made, where there was any definition for Library::OPTION1
And when I try to compile the sketch, this is what happens:
/var/folders/vb/rq_5f8jj11v06z8yq8pg3hdh0000gn/T//ccFt5nhS.ltrans0.ltrans.o: In function `__static_initialization_and_destruction_0':
/Users/michael/Arduino/test/test.ino:3: undefined reference to `Library::Library(unsigned long, char, Library::options)'
collect2: error: ld returned 1 exit status
exit status 1
Error compiling for board Arduino Nano.
Don't hide simple syntax like that behind macros. It hides the structure of the code from both humans and tools. Library::Option1 is simple, correct, and unambiguous.
Any decent IDE will automatically prepend Library:: if you enable autocomplete, and any C++ programmer should be familiar with that syntax. IMO, you're not doing your users a favor by introducing nonstandard macros.