I am attempting to write yet another class object for the DS1307.
I want to have a constructor that will accept the compile date and time constants as parameters. The constructor will parse the strings into time elements. It will then read previous time elements from the 56 bytes of ram also on the DS1307. If the times are different then the clock is reset to the compile time.
The works under the assumption that a sketch is compiled just before it is uploaded. And the sketch executes as soon as it is uploaded. Therefore, the clock will be reset to the clock time of the computer (allowing for the fact that there are some seconds between the time the sketch is compiled and when it executes).
My problem occurs at the point where I am reading the old values from the RAM. The sketch hangs at the endTransmission() call. My code looks like:
I suspect that the DS1307 constructor is being called before the Wire constructor. Since the Wire object isn't valid yet the Wire.begin() may be failing.
Rather than creating the object with date and time you might want to create the object empty and set the data and time at run time.
The DS1307 class has no member variable/properties. All the methods are 'static' so there is almost no reason to instantiate an object if I can not set the date in the constructor. There is no "Begin" for the DS1307 class and the I call the Wire.begin with I was getting the hang.
Exactly, I'm suggesting you pass the information to the constructor, but don't do anything on the bus till calling a method Begin() - ie write a Begin() and move the code to it. Then you get control of when things happen.
Or you can leave the constructor empty and define a function init() where you set the time and date.
In C++, the role of the constructor is to initialize the object memory.
This is too much to be doing in a constructor IMHO. Especially one which is for an object created statically.
Remember, after your constructor is called main is executed (since that is a function). The first thing main does is call init. The first thing init does is:
sei();
So, first problem. Interrupts are not enabled. And endTransmission uses interrupts.
If you create your object dynamically there shouldn't be a big problem. That is:
DS1307 * foo = new DS1307 (__DATE__, __TIME__);
(edit)
Preferably separating the two actions. eg.
DS1307 * foo; // declare it
void setup ()
{
foo = new DS1307 (__DATE__, __TIME__); // create an instance
...
}
But if you are going to do that you may as well just use the "foo.begin ()" idea.
Of course. I use this stripped down code just to set them time when I don't have a RTC and just need a reasonable time. Usually I am compiling and testing so much that the time is usually quite close.
When I have the DS1307 attached, I convert the time into 4 bytes and check them against the last 4 bytes in the clock's RAM (60-63). If they are different, I update the clock and store the bytes into the RAM. If they are the same, I use the clock's time.