#include #include #include #include #include //https://github.com/LennartHennigs/Button2 #include //https://github.com/claws/BH1750 #include //https://github.com/xreef/DHT12_sensor_library #include "ds18b20.h" #include "configuration.h" typedef enum { BME280_SENSOR_ID, DHTxx_SENSOR_ID, SHT3x_SENSOR_ID, BHT1750_SENSOR_ID, SOIL_SENSOR_ID, SALT_SENSOR_ID, DS18B20_SENSOR_ID, VOLTAGE_SENSOR_ID, } sensor_id_t; typedef struct { uint32_t timestamp; /**< time is in milliseconds */ float temperature; /**< temperature is in degrees centigrade (Celsius) */ float light; /**< light in SI lux units */ float pressure; /**< pressure in hectopascal (hPa) */ float humidity; /**< humidity in percent */ float altitude; /**< altitude in m */ float voltage; /**< voltage in volts (V) */ uint8_t soli; //Percentage of soil uint8_t salt; //Percentage of salt } higrow_sensors_event_t; BH1750 lightMeter(OB_BH1750_ADDRESS); //0x23 DHT12 dht12(DHT12_PIN, true); // Button2 button(BOOT_PIN); // Button2 useButton(USER_BUTTON); bool has_bmeSensor = true; bool has_lightSensor = true; bool has_dhtSensor = true; uint64_t timestamp = 0; #include //Provide the token generation process info. #include "addons/TokenHelper.h" //Provide the RTDB payload printing info and other helper functions. #include "addons/RTDBHelper.h" // Insert Firebase project API Key #define API_KEY "AIzaSyCHSaLiJYlosS2tgg7uQZt3ZUeQ7w7DHhE" // Insert RTDB URLefine the RTDB URL */ #define DATABASE_URL "https://plants-a388a-default-rtdb.europe-west1.firebasedatabase.app/" // #include // #include // WiFiUDP ntpUDP; // NTPClient timeClient(ntpUDP); String formattedDate; //Define Firebase Data object FirebaseData fbdo; FirebaseAuth auth; FirebaseConfig config; unsigned long sendDataPrevMillis = 0; bool signupOK = false; void deviceProbe(TwoWire &t); // void sleepHandler(Button2 &b) // { // Serial.println("Enter Deepsleep ..."); // esp_sleep_enable_ext1_wakeup(GPIO_SEL_35, ESP_EXT1_WAKEUP_ALL_LOW); // delay(1000); // esp_deep_sleep_start(); // } void setupWiFi() { WiFi.mode(WIFI_STA); Serial.print("Connect SSID:"); Serial.print(WIFI_SSID); Serial.print(" Password:"); Serial.println(WIFI_PASSWD); WiFi.begin(WIFI_SSID, WIFI_PASSWD); if (WiFi.waitForConnectResult() != WL_CONNECTED) { Serial.println("WiFi connect fail!"); delay(3000); esp_restart(); } Serial.print("WiFi connect success ! , "); Serial.print("IP Address: "); Serial.println(WiFi.localIP()); } bool get_higrow_sensors_event(sensor_id_t id, higrow_sensors_event_t &val) { memset(&val, 0, sizeof(higrow_sensors_event_t)); switch (id) { case DHTxx_SENSOR_ID: { val.temperature = dht12.readTemperature(); val.humidity = dht12.readHumidity(); if (isnan(val.temperature)) { val.temperature = 0.0; } if (isnan(val.humidity)) { val.humidity = 0.0; } } break; case BHT1750_SENSOR_ID: { if (has_lightSensor) { val.light = lightMeter.readLightLevel(); } else { val.light = 0; } } break; case SOIL_SENSOR_ID: { uint16_t soil = analogRead(SOIL_PIN); val.soli = map(soil, 0, 4095, 100, 0); } break; case SALT_SENSOR_ID: { uint8_t samples = 120; uint32_t humi = 0; uint16_t array[120]; for (int i = 0; i < samples; i++) { array[i] = analogRead(SALT_PIN); delay(2); } std::sort(array, array + samples); for (int i = 1; i < samples - 1; i++) { humi += array[i]; } humi /= samples - 2; val.salt = humi; } break; case VOLTAGE_SENSOR_ID: { int vref = 1100; uint16_t volt = analogRead(BAT_ADC); val.voltage = ((float)volt / 4095.0) * 6.6 * (vref); } break; default: break; } return true; } void setup() { Serial.begin(115200); // useButton.setLongClickHandler(sleepHandler); //! Sensor power control pin , use deteced must set high pinMode(POWER_CTRL, OUTPUT); digitalWrite(POWER_CTRL, 1); delay(1000); Wire.begin(I2C_SDA, I2C_SCL); deviceProbe(Wire); // timeClient.begin(); dht12.begin(); if (!lightMeter.begin()) { Serial.println(F("Could not find a valid BH1750 sensor, check wiring!")); has_lightSensor = false; } setupWiFi(); /* Assign the api key (required) */ config.api_key = API_KEY; /* Assign the RTDB URL (required) */ config.database_url = DATABASE_URL; if (Firebase.signUp(&config, &auth, "", "")){ Serial.println("ok"); signupOK = true; } else{ Serial.printf("%s\n", config.signer.signupError.message.c_str()); } /* Assign the callback function for the long running token generation task */ config.token_status_callback = tokenStatusCallback; //see addons/TokenHelper.h Firebase.begin(&config, &auth); Firebase.reconnectWiFi(true); } int count = 0; void loop() { // while(!timeClient.update()) { // timeClient.forceUpdate(); // } // formattedDate = timeClient.getFormattedDate(); // button.loop(); // useButton.loop(); higrow_sensors_event_t val = {0}; get_higrow_sensors_event(DHTxx_SENSOR_ID, val); FirebaseJson json; json.set("humidity", val.humidity); json.set("temperature", val.temperature); // json.set("time", formattedDate); if (Firebase.ready() && signupOK && (millis() - sendDataPrevMillis > 15000 || sendDataPrevMillis == 0)){ if (Firebase.RTDB.pushJSON(&fbdo, "/test/data", &json)){ Serial.println("PASSED"); Serial.println("PATH: " + fbdo.dataPath()); Serial.println("TYPE: " + fbdo.dataType()); } else { Serial.println("FAILED"); Serial.println("REASON: " + fbdo.errorReason()); } } } void deviceProbe(TwoWire &t) { uint8_t err, addr; int nDevices = 0; for (addr = 1; addr < 127; addr++) { t.beginTransmission(addr); err = t.endTransmission(); if (err == 0) { Serial.print("I2C device found at address 0x"); if (addr < 16) Serial.print("0"); Serial.print(addr, HEX); Serial.println(" !"); switch (addr) { case OB_BH1750_ADDRESS: has_dhtSensor = true; break; case OB_BME280_ADDRESS: has_bmeSensor = true; break; case OB_SHT3X_ADDRESS: has_dhtSensor = true; break; default: break; } nDevices++; } else if (err == 4) { Serial.print("Unknow error at address 0x"); if (addr < 16) Serial.print("0"); Serial.println(addr, HEX); } } if (nDevices == 0) Serial.println("No I2C devices found\n"); else Serial.println("done\n"); }