Hi knowledgeable ones,
I have been struggling to solve this for over a week now and searched hundreds of topics but yet to find a solution.
I have a datalogging program that works fine. I thought I would enhance it by appending a header at midnight, I have included NTP protocol and get time from it. But I cannot find a way of extracting Hour, minutes and seconds to put into an 'if' statement.
I have the section of code that reflects my problem, if I can get this working with your help I can incorporate it into my main program.
I have highlighted where I fail in the code below.
When trying to compile the error statement is "c++ forbids comparison between pointer and integer [-fpermissive]" So I need to extract or covert the data from the array at that point.
Thanks for your help
Dave
#include <Arduino.h>
#include <WiFi.h>
#include <AsyncTCP.h>
#include <ESPAsyncWebServer.h>
#include "FS.h"
#include "SD.h"
#include "SPI.h"
#include "time.h"
// Replace with your network credentials
const char* ssid = "ssid";
const char* ssid = "password";
const char* ntpServer = "pool.ntp.org";
const long gmtOffset_sec = 0;
const int daylightOffset_sec = 3600;
void setup() {
Serial.begin(9600);
Serial.println("Initiaiase WiFi");
WiFi.mode(WIFI_STA);
WiFi.begin(ssid, password);
Serial.print("Connecting to WiFi ..");
while (WiFi.status() != WL_CONNECTED) {
Serial.print('.');
delay(1000);
}
Serial.println(WiFi.localIP());
long rssi = WiFi.RSSI();
Serial.print("RSSI:");
Serial.println(rssi);
configTime(gmtOffset_sec, daylightOffset_sec, ntpServer);
struct tm timeinfo;
if (!getLocalTime(&timeinfo)) {
Serial.println("Failed to obtain time");
return;
}
Serial.println(&timeinfo, "%A, %B %d %Y %H:%M:%S");
}
void loop() {
struct tm timeinfo;
if (!getLocalTime(&timeinfo)) {
Serial.println("Failed to obtain time");
return;
}
Serial.println(&timeinfo, "%A, %B %d %Y %H:%M:%S");
char output_hours [3];
strftime(output_hours, 3, "%H", &timeinfo);
char output_minutes [3];
strftime(output_minutes, 3, "%M", &timeinfo);
char output_seconds [3];
strftime(output_seconds, 3, "%S", &timeinfo);
Serial.print("output_hours = ");
Serial.println(output_hours);
Serial.print("output_Minutes = ");
Serial.println(output_minutes);
Serial.print("output_Seconds = ");
Serial.println(output_seconds);
delay(1000);
//////***********Everything works up to this point
///// What I want to do now is something like this
if (output_hours == 00) {
do something like
Serial.println("Success");
}
else {
Serial.println("Failure");
}
}
struct tm timeinfo;
if (!getLocalTime(&timeinfo)) {
Serial.println("Failed to obtain time");
return;
}
and a struct tm looks like this
struct tm {
int8_t tm_sec; /**< seconds after the minute - [ 0 to 59 ] */
int8_t tm_min; /**< minutes after the hour - [ 0 to 59 ] */
int8_t tm_hour; /**< hours since midnight - [ 0 to 23 ] */
int8_t tm_mday; /**< day of the month - [ 1 to 31 ] */
int8_t tm_wday; /**< days since Sunday - [ 0 to 6 ] */
int8_t tm_mon; /**< months since January - [ 0 to 11 ] */
int16_t tm_year; /**< years since 1900 */
int16_t tm_yday; /**< days since January 1 - [ 0 to 365 ] */
int16_t tm_isdst; /**< Daylight Saving Time flag */
};
so if your struct is correct, then it's quite easy to get the hour or minute etc
Here is a demo-code that shows how it can be done
some home-WLAN-Routers can be used as a NTP-server too
At least WLAN-Routers from AVM called Fritz!Box
#include <WiFi.h>
unsigned long MyTestTimer = 0; // variables MUST be of type unsigned long
const byte OnBoard_LED = 2;
//const char *ssid = "";
const char *ssid = "";
const char *password = "";
// a lot of home-wlan-routers can be used as a NTP-server too
const char* ntpServer = "fritz.box";
const long gmtOffset_sec = 0;
const int daylightOffset_sec = 7200;
#include <time.h> // time() ctime()
time_t now; // this is the epoch
tm myTimeInfo; // the structure tm holds time information in a more convient way
void showTime() {
time(&now); // read the current time
localtime_r(&now, &myTimeInfo); // update the structure tm with the current time
Serial.print("year:");
Serial.print(myTimeInfo.tm_year + 1900); // years since 1900
Serial.print("\tmonth:");
Serial.print(myTimeInfo.tm_mon + 1); // January = 0 (!)
Serial.print("\tday:");
Serial.print(myTimeInfo.tm_mday); // day of month
Serial.print("\thour:");
Serial.print(myTimeInfo.tm_hour); // hours since midnight 0-23
Serial.print("\tmin:");
Serial.print(myTimeInfo.tm_min); // minutes after the hour 0-59
Serial.print("\tsec:");
Serial.print(myTimeInfo.tm_sec); // seconds after the minute 0-61*
Serial.print("\twday");
Serial.print(myTimeInfo.tm_wday); // days since Sunday 0-6
if (myTimeInfo.tm_isdst == 1) // Daylight Saving Time flag
Serial.print("\tDST");
else
Serial.print("\tstandard");
Serial.println();
}
void connectToWifi() {
Serial.print("Connecting to ");
Serial.println(ssid);
WiFi.persistent(false);
WiFi.mode(WIFI_STA);
WiFi.begin(ssid, password);
while (WiFi.status() != WL_CONNECTED) {
BlinkHeartBeatLED(OnBoard_LED, 333);
delay(332);
Serial.print(".");
}
Serial.print("\n connected.");
Serial.println(WiFi.localIP() );
}
void synchroniseWith_NTP_Time() {
Serial.print("configTime uses ntpServer ");
Serial.println(ntpServer);
configTime(gmtOffset_sec, daylightOffset_sec, ntpServer);
Serial.print("synchronising time");
while (myTimeInfo.tm_year + 1900 < 2000 ) {
time(&now); // read the current time
localtime_r(&now, &myTimeInfo);
BlinkHeartBeatLED(OnBoard_LED, 100);
delay(100);
Serial.print(".");
}
Serial.print("\n time synchronsized \n");
showTime();
}
void PrintFileNameDateTime() {
Serial.println( F("Code running comes from file ") );
Serial.println(__FILE__);
Serial.print( F(" compiled ") );
Serial.print(__DATE__);
Serial.print( F(" ") );
Serial.println(__TIME__);
}
boolean TimePeriodIsOver (unsigned long &periodStartTime, unsigned long TimePeriod) {
unsigned long currentMillis = millis();
if ( currentMillis - periodStartTime >= TimePeriod )
{
periodStartTime = currentMillis; // set new expireTime
return true; // more time than TimePeriod) has elapsed since last time if-condition was true
}
else return false; // not expired
}
void BlinkHeartBeatLED(int IO_Pin, int BlinkPeriod) {
static unsigned long MyBlinkTimer;
pinMode(IO_Pin, OUTPUT);
if ( TimePeriodIsOver(MyBlinkTimer,BlinkPeriod) ) {
digitalWrite(IO_Pin,!digitalRead(IO_Pin) );
}
}
void setup() {
Serial.begin(115200);
Serial.println("\n Setup-Start \n");
PrintFileNameDateTime();
connectToWifi();
synchroniseWith_NTP_Time();
}
void loop() {
BlinkHeartBeatLED(OnBoard_LED,100);
if ( TimePeriodIsOver(MyTestTimer,1000) ) {
showTime();
}
}
PLEASE use code tags when posting code (edit your post #10 and add code tags)
You need to read about structures.
you don't need an additional variable, the variable is timeinfo and it holds the data in its attributes timeinfo.tm_hour and timeinfo.tm_min...
you can do
if ((timeinfo.tm_hour == 0) && (timeinfo.tm_min == 0)) {
... // do something here
}
note that you'll be at midnight for a whole minute so if it's just like this in the loop(), you will do this many thousands times possibly as the condition will be true for 60,000,000µs
If you want to assign it to a variable anyway you have to find out what the datatype of
.tm_hour
.tm_min
is.
This is done this way:
looking up what is the filename of the library where the "time-Data" is defined
in this case this is #include <time.h>
So you search on your harddisk for the filename "time.h"
make a copy of that file to make sure that some accidently happened changes do not affect the original file
after making a copy of the file open the copy
time copy.h with the arduino-IDE or any other texteditor like Notepad++ or editor.exe
".tm_hour" means the "variable is part of a "struct" with name "tm"
and voila there are the datatypes
struct tm {
int8_t tm_sec; /**< seconds after the minute - [ 0 to 59 ] */
int8_t tm_min; /**< minutes after the hour - [ 0 to 59 ] */
int8_t tm_hour; /**< hours since midnight - [ 0 to 23 ] */
int8_t tm_mday; /**< day of the month - [ 1 to 31 ] */
int8_t tm_wday; /**< days since Sunday - [ 0 to 6 ] */
int8_t tm_mon; /**< months since January - [ 0 to 11 ] */
int16_t tm_year; /**< years since 1900 */
int16_t tm_yday; /**< days since January 1 - [ 0 to 365 ] */
int16_t tm_isdst; /**< Daylight Saving Time flag */
};
tm_hour, tm_min are all uint8_t which is basically the same as "byte"
Hi J-M-L
Thanks very much for your info, really helpful as are the others who have posted.
I was looking to see how to add code tags to my earlier post when your reply arrived and hopefully I can amend it. Thanks
Thanks very much
I am very new to this coding and I am learning as I go along.
I am a retired Instrumentation guy, hardware has been my life and now I trying coding as a hobby.
I managed to post my original code as per the guidelines, just didn't think about it in my replies.
but you are never to old to learn
Thanks