-
Notifications
You must be signed in to change notification settings - Fork 58
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
support for alternate or multiple i2c buses #30
Comments
Just my 2 cents, I have also encountered this problem, and I have tried this simple solution with passing in a pointer to a HardwareI2C instance in the constructor, setting the default to Wire, like so class hd44780_I2Clcd : public hd44780
{
public:
hd44780_I2Clcd(uint8_t i2c_addr=0, HardwareI2C *wire=&Wire) : _Addr(i2c_addr), _I2Cbus(wire) {}
//...
private:
HardwareI2C *_I2Cbus; And then replacing all accesses to Wire like this _I2Cbus->begin(); The alternative would be to use the Stream class from which HardwareI2C inherits, which is a bit too generic, and I don't know how many alternative Wire library implementations even use that. I agree that templates would seem to be the way to go if either HardwareI2C or Stream isn't usable with the majority (all?) of libraries. While this is your choice to make, I am not sure if requiring a newer version of the Arduino IDE is that much of a constraint? Surely any user starting off just goes to arduino.cc and downloads the latest? |
It is more complicated than you are thinking especially when looking across many different i2c libraries and many different h/w platforms. i.e. you can't ever hardcode any classname or object name because the class name for the i2c interface and the default wire object name is not the same on all h/w platforms and/or i2c libraries. It is better to use a templated class with parameters than to pass in constructor parameters since using constructor parameters requires using known types and a known object name if using a default. These names vary across environments. More below It is theoretically possible to make it fully backward compatible with today's hd44780 i2c i/o classes. Currently there is simply is no way to provide full backward compatibility and full portability across all h/w platforms while allowing the users to configure the i2c wire interface used for the hd44780 i/o class objects in their sketch. My current solution (which I have working ) creates new i/o classes using templates that require the user to pass in some template parameters (not constructor parameters). Even if using a templated class to resolve the i2c class name and object name differences, I already have working solutions that do not depend on C++ 17 for two new i/o classes:
Here is what the class declaration looks like:
and all the i2c object references in the code become: etc... The sketch code object declaration is a bit funky looking since the user must specify the i2c class and i2c object. Where Wire is the name of the i2c object to be used. It is not the name of the i2c library. If C++ 17 was available, the first parameter could be eliminated to allow this: since auto could be used instead of having to specify the type. One thing that I'm still wrestling with is whether to toss these new i/o classes into the hd44780 library There are advantages and disadvantages to bundling vs having separate libraries. |
The i/o classes that use i2c (currently hd44780_I2Cexp and hd44780_I2Clcd) are hardcoded to use an i2c wire library object named Wire
While this can be worked around using a macro as shown in issue #29
not only is that work around "ugly" but it is not optimal since does not allow assigning a bus object on a per lcd object instance.
i.e. all lcd objects must use the same Wire library object which means that they must all be on the same bus.
The solution is to pass the i/o class a Wire library object information when the constructor is declared & defined.
While a simple solution would be to simply pass in a pointer to the desired Wire library object, this is cannot be implemented in a portable way given that not all Wire libraries use the same class name for their Wire object.
There are various ways to handle this, most revolve around making the classes templated classes.
Where things get messy is that some of the more user friendly ways to handle it require much newer version of the compiler tools to use newer capabilities of the C++ standard.
I will have to balance ease of use, with backward compatibility capabilities, and tool set availability to try to ensure the widest amount of portability across not only versions of the Arduino IDE but also across the 3rd party hardware board package addons.
The text was updated successfully, but these errors were encountered: