├── README.md ├── MatrixClock_ESP8266_DHT_2.ino ├── MatrixClock_ESP8266_DHT.ino ├── MatrixClock_ESP8266_DHT_1.ino └── MatrixClock_ESP8266_DHT_3.ino /README.md: -------------------------------------------------------------------------------- 1 | # NOTE: You must change line Serial.println(String(WiFi.localIP()); in Serial.println(WiFi.localIP()); !!!! 2 | 3 | # ESP8266-LED-Matrix-Clock 4 | inspired by https://github.com/schreibfaul1/ESP8266-LED-Matrix-Clock 5 | 6 | my articles: 7 | - https://nicuflorica.blogspot.com/2019/03/ceas-matriceal-animat-cu-esp8266-si-rtc.html 8 | 9 | - https://nicuflorica.blogspot.com/2019/04/ceas-matriceal-animat-cu-esp8266-si-rtc.html 10 | 11 | - https://nicuflorica.blogspot.com/2019/04/ceas-matriceal-animat-cu-esp8266-si-rtc_11.html 12 | 13 | - http://nicuflorica.blogspot.com/2019/05/ceas-matriceal-animat-cu-esp8266-si-rtc.html 14 | 15 | - http://nicuflorica.blogspot.com/2019/09/ceas-matriceal-animat-cu-esp8266-si-rtc.html 16 | 17 | 18 | ![ceas](https://4.bp.blogspot.com/-sPenR_UCMYA/XKEeiTulrlI/AAAAAAAAY7A/pjJxiMm3iCo-j3SLFzuTvmfkJRRP7LP2wCLcBGAs/s1600/ceas0.jpg) 19 | 20 | NOTE: LAST STABLE VERSION IS /MatrixClock_ESP8266_DHT_3e1.ino ! 21 | 22 | classical clock: 23 | ![schematic](https://3.bp.blogspot.com/--UePMiKRmFs/XKEjsCvku6I/AAAAAAAAY70/pDLfakXD7fcyVTAXzI74wH5Jl8OpZm4DgCLcBGAs/s1600/ESP8266_LED_Matrix_Clock_DHT.gif) 24 | 25 | schematic with automatic brightness (using LDR = photoresistor): 26 | ![schematic2](https://4.bp.blogspot.com/-OyIs9oE8in8/XK9-Zm2RxzI/AAAAAAAAZCg/a2TihedTq501hoK6mNFIUM-Fo1CypZZcgCLcBGAs/s1600/ESP8266_LED_Matrix_Clock_DHT_LDR.gif) 27 | -------------------------------------------------------------------------------- /MatrixClock_ESP8266_DHT_2.ino: -------------------------------------------------------------------------------- 1 | //********************************************************************************************************* 2 | //* ESP8266 MatrixClock by Wolle / schreibfaul1 * 3 | //********************************************************************************************************* 4 | // 5 | // first release on 26.02.2017 6 | // updated on 26.03.2019 7 | // Version 1.2.1 8 | // https://github.com/schreibfaul1/ESP8266-LED-Matrix-Clock 9 | // 10 | // THE SOFTWARE IS PROVIDED "AS IS" FOR PRIVATE USE ONLY, IT IS NOT FOR COMMERCIAL USE IN WHOLE OR PART OR CONCEPT. 11 | // FOR PERSONAL USE IT IS SUPPLIED WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE 12 | // WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHOR 13 | // OR COPYRIGHT HOLDER BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR 14 | // OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE 15 | // 16 | // 17 | // small changes by Nicu FLORICA (niq_ro), 31-May_2019 18 | // add DHT sensor for temperature and humidity 19 | // change at add text to be more easy to change 20 | // change temperature to be as float 21 | 22 | #include 23 | #include 24 | #include 25 | #include 26 | #include 27 | #include 28 | #include 29 | #include "DHT.h" 30 | 31 | #define SDA 5 // Pin sda (I2C) 32 | #define SCL 4 // Pin scl (I2C) 33 | #define CS 15 // Pin cs (SPI) 34 | #define anzMAX 6 // Anzahl der kaskadierten Module 35 | 36 | char ssid[] = "network name"; // your network SSID (name) 37 | char pass[] = "password"; // your network password 38 | 39 | // other displays ------------------------------------- 40 | #define REVERSE_HORIZONTAL // Parola, Generic and IC-Station 41 | //#define REVERSE_VERTICAL // IC-Station display 42 | #define ROTATE_90 // Generic display 43 | /* 44 | p A B C D E F G 7 6 5 4 3 2 1 0 G F E D C B A p G F E D C B A p 45 | ------------------------ ------------------------ ------------------------ ------------------------ 46 | 0 |o o o o o o o o| p |o o o o o o o o| 0 |o o o o o o o o| 7 |o o o o o o o o| 47 | 1 |o o o o o o o o| A |o o o o o o o o| 1 |o o o o o o o o| 6 |o o o o o o o o| 48 | 2 |o o o o o o o o| B |o o o o o o o o| 2 |o o o o o o o o| 5 |o o o o o o o o| 49 | 3 |o o o o| C |o o o o| 3 |o o o o| 4 |o o o o| 50 | 4 |o o FC-16 o o| D |o o Generic o o| 4 |o o Parola o o| 3 |o o IC-Station o o| 51 | 5 |o o o o| E |o o o o| 5 |o o o o| 2 |o o o o| 52 | 6 |o o o o o o o o| F |o o o o o o o o| 6 |o o o o o o o o| 1 |o o o o o o o o| 53 | 7 |o o o o o o o o| G |o o o o o o o o| 7 |o o o o o o o o| 0 |o o o o o o o o| 54 | ------------------------ ------------------------ ------------------------ ------------------------ 55 | */ 56 | 57 | // DHT sensor 58 | #define DHTPIN 12 // what pin we're connected to // GPIO 13 = D6 59 | // Uncomment whatever type you're using! 60 | //#define DHTTYPE DHT11 // DHT 11 61 | #define DHTTYPE DHT22 // DHT 22 (AM2302) 62 | //#define DHTTYPE DHT21 // DHT 21 (AM2301) 63 | // Connect pin 1 (on the left) of the sensor to +5V 64 | // NOTE: If using a board with 3.3V logic like an Arduino Due connect pin 1 65 | // to 3.3V instead of 5V! 66 | // Connect pin 2 of the sensor to whatever your DHTPIN is 67 | // Connect pin 4 (on the right) of the sensor to GROUND 68 | // Connect a 10K resistor from pin 2 (data) to pin 1 (power) of the sensor 69 | // Initialize DHT sensor for normal 16mhz Arduino 70 | //DHT dht(DHTPIN, DHTTYPE); 71 | // NOTE: For working with a faster chip, like an Arduino Due or Teensy, you 72 | // might need to increase the threshold for cycle counts considered a 1 or 0. 73 | // You can do this by passing a 3rd parameter for this threshold. It's a bit 74 | // of fiddling to find the right value, but in general the faster the CPU the 75 | // higher the value. The default for a 16mhz AVR is a value of 6. For an 76 | // Arduino Due that runs at 84mhz a value of 30 works. 77 | // Example to initialize DHT sensor for Arduino Due: 78 | DHT dht(DHTPIN, DHTTYPE, 11); // for ESP8266 79 | 80 | 81 | unsigned short maxPosX = anzMAX * 8 - 1; //calculated maxposition 82 | unsigned short LEDarr[anzMAX][8]; //character matrix to display (40*8) 83 | unsigned short helpArrMAX[anzMAX * 8]; //helperarray for chardecoding 84 | unsigned short helpArrPos[anzMAX * 8]; //helperarray pos of chardecoding 85 | unsigned int z_PosX = 0; //xPosition im Display für Zeitanzeige 86 | unsigned int d_PosX = 0; //xPosition im Display f�r Datumanzeige 87 | bool f_tckr1s = false; 88 | bool f_tckr50ms = false; 89 | bool f_tckr24h = false; 90 | unsigned long epoch = 0; 91 | unsigned int localPort = 2390; // local port to listen for UDP packets 92 | const char* ntpServerName = "time.nist.gov"; 93 | const int NTP_PACKET_SIZE = 48; // NTP time stamp is in the first 48 bytes of the message 94 | byte packetBuffer[NTP_PACKET_SIZE]; //buffer to hold incoming and outgoing packets 95 | IPAddress timeServerIP; // time.nist.gov NTP server address 96 | tm *tt, ttm; 97 | #define corectie +1 98 | 99 | float temperatura = 0; 100 | int temp, tempz, tempu, temps, tempr = 0; 101 | byte minus = 0; 102 | int umiditate = 0; 103 | int poz, poz2; 104 | int mult = 0; 105 | 106 | //Variablen für RTC DS3231 107 | const unsigned char DS3231_ADDRESS = 0x68; 108 | const unsigned char secondREG = 0x00; 109 | const unsigned char minuteREG = 0x01; 110 | const unsigned char hourREG = 0x02; 111 | const unsigned char WTREG = 0x03; //weekday 112 | const unsigned char dateREG = 0x04; 113 | const unsigned char monthREG = 0x05; 114 | const unsigned char yearREG = 0x06; 115 | const unsigned char alarm_min1secREG = 0x07; 116 | const unsigned char alarm_min1minREG = 0x08; 117 | const unsigned char alarm_min1hrREG = 0x09; 118 | const unsigned char alarm_min1dateREG = 0x0A; 119 | const unsigned char alarm_min2minREG = 0x0B; 120 | const unsigned char alarm_min2hrREG = 0x0C; 121 | const unsigned char alarm_min2dateREG = 0x0D; 122 | const unsigned char controlREG = 0x0E; 123 | const unsigned char statusREG = 0x0F; 124 | const unsigned char ageoffsetREG = 0x10; 125 | const unsigned char tempMSBREG = 0x11; 126 | const unsigned char tempLSBREG = 0x12; 127 | const unsigned char _24_hour_format = 0; 128 | const unsigned char _12_hour_format = 1; 129 | const unsigned char AM = 0; 130 | const unsigned char PM = 1; 131 | 132 | struct DateTime { 133 | unsigned short sek1, sek2, sek12, min1, min2, min12, std1, std2, std12; 134 | unsigned short tag1, tag2, tag12, mon1, mon2, mon12, jahr1, jahr2, jahr12, WT; 135 | } MEZ; 136 | 137 | 138 | // The object for the Ticker 139 | Ticker tckr; 140 | // A UDP instance to let us send and receive packets over UDP 141 | WiFiUDP udp; 142 | 143 | 144 | //months 145 | char M_arr[12][5] = { { ' ', 'J', 'a', 'n', ' ' }, { ' ', 'F', 'e', 'b', ' ' }, 146 | { ' ', 'M', 'a', 'r', ' ' }, { ' ', 'A', 'p', 'r', ' ' }, { ' ', 'M', 'a', 147 | 'y', ' ' }, { ' ', 'J', 'u', 'n', 'e' }, { ' ', 'J', 'u', 'l', 'y' }, { 148 | ' ', 'A', 'u', 'g', ' ' }, { ' ', 'S', 'e', 'p', 't' }, { ' ', 'O', 'c', 149 | 't', ' ' }, { ' ', 'N', 'o', 'v', ' ' }, { ' ', 'D', 'e', 'c', ' ' } }; 150 | //days 151 | char WT_arr[7][4] = { { 'S', 'u', 'n', ' ' }, { 'M', 'o', 'n', ' ' }, { 'T', 'u', 'e', ' ' }, { 152 | 'W', 'e', 'd', ' ' }, { 'T', 'h', 'u', ' ' }, { 'F', 'r', 'i', ' ' }, { 'S', 'a', 't', ' ' } }; 153 | 154 | // Zeichensatz 5x8 in einer 8x8 Matrix, 0,0 ist rechts oben 155 | unsigned short const font1[96][9] = { 156 | { 0x07, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00 }, // 0x20, Space 157 | { 0x07, 0x04, 0x04, 0x04, 0x04, 0x04, 0x00, 0x04, 0x00 }, // 0x21, ! 158 | { 0x07, 0x09, 0x09, 0x12, 0x00, 0x00, 0x00, 0x00, 0x00 }, // 0x22, " 159 | { 0x07, 0x0a, 0x0a, 0x1f, 0x0a, 0x1f, 0x0a, 0x0a, 0x00 }, // 0x23, # 160 | // { 0x07, 0x04, 0x0f, 0x14, 0x0e, 0x05, 0x1e, 0x04, 0x00 }, // 0x24, $ 161 | { 0x07, 0x06, 0x09, 0x09, 0x06, 0x00, 0x00, 0x00, 0x00 }, // 0x24, $ changed with degree sign 162 | { 0x07, 0x19, 0x19, 0x02, 0x04, 0x08, 0x13, 0x13, 0x00 }, // 0x25, % 163 | { 0x07, 0x04, 0x0a, 0x0a, 0x0a, 0x15, 0x12, 0x0d, 0x00 }, // 0x26, & 164 | { 0x07, 0x04, 0x04, 0x08, 0x00, 0x00, 0x00, 0x00, 0x00 }, // 0x27, ' 165 | { 0x07, 0x02, 0x04, 0x08, 0x08, 0x08, 0x04, 0x02, 0x00 }, // 0x28, ( 166 | { 0x07, 0x08, 0x04, 0x02, 0x02, 0x02, 0x04, 0x08, 0x00 }, // 0x29, ) 167 | { 0x07, 0x04, 0x15, 0x0e, 0x1f, 0x0e, 0x15, 0x04, 0x00 }, // 0x2a, * 168 | { 0x07, 0x00, 0x04, 0x04, 0x1f, 0x04, 0x04, 0x00, 0x00 }, // 0x2b, + 169 | { 0x04, 0x00, 0x00, 0x00, 0x00, 0x00, 0x01, 0x01, 0x02 }, // 0x2c, , 170 | { 0x07, 0x00, 0x00, 0x00, 0x1f, 0x00, 0x00, 0x00, 0x00 }, // 0x2d, - 171 | { 0x04, 0x00, 0x00, 0x00, 0x00, 0x00, 0x03, 0x03, 0x00 }, // 0x2e, . 172 | { 0x07, 0x01, 0x01, 0x02, 0x04, 0x08, 0x10, 0x10, 0x00 }, // 0x2f, / 173 | { 0x07, 0x0e, 0x11, 0x13, 0x15, 0x19, 0x11, 0x0e, 0x00 }, // 0x30, 0 174 | { 0x07, 0x04, 0x0c, 0x04, 0x04, 0x04, 0x04, 0x0e, 0x00 }, // 0x31, 1 175 | { 0x07, 0x0e, 0x11, 0x01, 0x02, 0x04, 0x08, 0x1f, 0x00 }, // 0x32, 2 176 | { 0x07, 0x0e, 0x11, 0x01, 0x06, 0x01, 0x11, 0x0e, 0x00 }, // 0x33, 3 177 | { 0x07, 0x02, 0x06, 0x0a, 0x12, 0x1f, 0x02, 0x02, 0x00 }, // 0x34, 4 178 | { 0x07, 0x1f, 0x10, 0x1e, 0x01, 0x01, 0x11, 0x0e, 0x00 }, // 0x35, 5 179 | { 0x07, 0x06, 0x08, 0x10, 0x1e, 0x11, 0x11, 0x0e, 0x00 }, // 0x36, 6 180 | { 0x07, 0x1f, 0x01, 0x02, 0x04, 0x08, 0x08, 0x08, 0x00 }, // 0x37, 7 181 | { 0x07, 0x0e, 0x11, 0x11, 0x0e, 0x11, 0x11, 0x0e, 0x00 }, // 0x38, 8 182 | { 0x07, 0x0e, 0x11, 0x11, 0x0f, 0x01, 0x02, 0x0c, 0x00 }, // 0x39, 9 183 | { 0x04, 0x00, 0x03, 0x03, 0x00, 0x03, 0x03, 0x00, 0x00 }, // 0x3a, : 184 | { 0x07, 0x00, 0x0c, 0x0c, 0x00, 0x0c, 0x04, 0x08, 0x00 }, // 0x3b, ; 185 | { 0x07, 0x02, 0x04, 0x08, 0x10, 0x08, 0x04, 0x02, 0x00 }, // 0x3c, < 186 | { 0x07, 0x00, 0x00, 0x1f, 0x00, 0x1f, 0x00, 0x00, 0x00 }, // 0x3d, = 187 | { 0x07, 0x08, 0x04, 0x02, 0x01, 0x02, 0x04, 0x08, 0x00 }, // 0x3e, > 188 | { 0x07, 0x0e, 0x11, 0x01, 0x02, 0x04, 0x00, 0x04, 0x00 }, // 0x3f, ? 189 | { 0x07, 0x0e, 0x11, 0x17, 0x15, 0x17, 0x10, 0x0f, 0x00 }, // 0x40, @ 190 | { 0x07, 0x04, 0x0a, 0x11, 0x11, 0x1f, 0x11, 0x11, 0x00 }, // 0x41, A 191 | { 0x07, 0x1e, 0x11, 0x11, 0x1e, 0x11, 0x11, 0x1e, 0x00 }, // 0x42, B 192 | { 0x07, 0x0e, 0x11, 0x10, 0x10, 0x10, 0x11, 0x0e, 0x00 }, // 0x43, C 193 | { 0x07, 0x1e, 0x09, 0x09, 0x09, 0x09, 0x09, 0x1e, 0x00 }, // 0x44, D 194 | { 0x07, 0x1f, 0x10, 0x10, 0x1c, 0x10, 0x10, 0x1f, 0x00 }, // 0x45, E 195 | { 0x07, 0x1f, 0x10, 0x10, 0x1f, 0x10, 0x10, 0x10, 0x00 }, // 0x46, F 196 | { 0x07, 0x0e, 0x11, 0x10, 0x10, 0x13, 0x11, 0x0f, 0x00 }, // 0x37, G 197 | { 0x07, 0x11, 0x11, 0x11, 0x1f, 0x11, 0x11, 0x11, 0x00 }, // 0x48, H 198 | { 0x07, 0x0e, 0x04, 0x04, 0x04, 0x04, 0x04, 0x0e, 0x00 }, // 0x49, I 199 | { 0x07, 0x1f, 0x02, 0x02, 0x02, 0x02, 0x12, 0x0c, 0x00 }, // 0x4a, J 200 | { 0x07, 0x11, 0x12, 0x14, 0x18, 0x14, 0x12, 0x11, 0x00 }, // 0x4b, K 201 | { 0x07, 0x10, 0x10, 0x10, 0x10, 0x10, 0x10, 0x1f, 0x00 }, // 0x4c, L 202 | { 0x07, 0x11, 0x1b, 0x15, 0x11, 0x11, 0x11, 0x11, 0x00 }, // 0x4d, M 203 | { 0x07, 0x11, 0x11, 0x19, 0x15, 0x13, 0x11, 0x11, 0x00 }, // 0x4e, N 204 | { 0x07, 0x0e, 0x11, 0x11, 0x11, 0x11, 0x11, 0x0e, 0x00 }, // 0x4f, O 205 | { 0x07, 0x1e, 0x11, 0x11, 0x1e, 0x10, 0x10, 0x10, 0x00 }, // 0x50, P 206 | { 0x07, 0x0e, 0x11, 0x11, 0x11, 0x15, 0x12, 0x0d, 0x00 }, // 0x51, Q 207 | { 0x07, 0x1e, 0x11, 0x11, 0x1e, 0x14, 0x12, 0x11, 0x00 }, // 0x52, R 208 | { 0x07, 0x0e, 0x11, 0x10, 0x0e, 0x01, 0x11, 0x0e, 0x00 }, // 0x53, S 209 | { 0x07, 0x1f, 0x04, 0x04, 0x04, 0x04, 0x04, 0x04, 0x00 }, // 0x54, T 210 | { 0x07, 0x11, 0x11, 0x11, 0x11, 0x11, 0x11, 0x0e, 0x00 }, // 0x55, U 211 | { 0x07, 0x11, 0x11, 0x11, 0x11, 0x11, 0x0a, 0x04, 0x00 }, // 0x56, V 212 | { 0x07, 0x11, 0x11, 0x11, 0x15, 0x15, 0x1b, 0x11, 0x00 }, // 0x57, W 213 | { 0x07, 0x11, 0x11, 0x0a, 0x04, 0x0a, 0x11, 0x11, 0x00 }, // 0x58, X 214 | { 0x07, 0x11, 0x11, 0x0a, 0x04, 0x04, 0x04, 0x04, 0x00 }, // 0x59, Y 215 | { 0x07, 0x1f, 0x01, 0x02, 0x04, 0x08, 0x10, 0x1f, 0x00 }, // 0x5a, Z 216 | { 0x07, 0x0e, 0x08, 0x08, 0x08, 0x08, 0x08, 0x0e, 0x00 }, // 0x5b, [ 217 | { 0x07, 0x10, 0x10, 0x08, 0x04, 0x02, 0x01, 0x01, 0x00 }, // 0x5c, '\' 218 | { 0x07, 0x0e, 0x02, 0x02, 0x02, 0x02, 0x02, 0x0e, 0x00 }, // 0x5d, ] 219 | { 0x07, 0x04, 0x0a, 0x11, 0x00, 0x00, 0x00, 0x00, 0x00 }, // 0x5e, ^ 220 | { 0x07, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x1f, 0x00 }, // 0x5f, _ 221 | { 0x07, 0x04, 0x04, 0x02, 0x00, 0x00, 0x00, 0x00, 0x00 }, // 0x60, ` 222 | { 0x07, 0x00, 0x0e, 0x01, 0x0d, 0x13, 0x13, 0x0d, 0x00 }, // 0x61, a 223 | { 0x07, 0x10, 0x10, 0x10, 0x1c, 0x12, 0x12, 0x1c, 0x00 }, // 0x62, b 224 | { 0x07, 0x00, 0x00, 0x00, 0x0e, 0x10, 0x10, 0x0e, 0x00 }, // 0x63, c 225 | { 0x07, 0x01, 0x01, 0x01, 0x07, 0x09, 0x09, 0x07, 0x00 }, // 0x64, d 226 | { 0x07, 0x00, 0x00, 0x0e, 0x11, 0x1f, 0x10, 0x0f, 0x00 }, // 0x65, e 227 | { 0x07, 0x06, 0x09, 0x08, 0x1c, 0x08, 0x08, 0x08, 0x00 }, // 0x66, f 228 | { 0x07, 0x00, 0x0e, 0x11, 0x13, 0x0d, 0x01, 0x01, 0x0e }, // 0x67, g 229 | { 0x07, 0x10, 0x10, 0x10, 0x16, 0x19, 0x11, 0x11, 0x00 }, // 0x68, h 230 | { 0x05, 0x00, 0x02, 0x00, 0x06, 0x02, 0x02, 0x07, 0x00 }, // 0x69, i 231 | { 0x07, 0x00, 0x02, 0x00, 0x06, 0x02, 0x02, 0x12, 0x0c }, // 0x6a, j 232 | { 0x07, 0x10, 0x10, 0x12, 0x14, 0x18, 0x14, 0x12, 0x00 }, // 0x6b, k 233 | { 0x05, 0x06, 0x02, 0x02, 0x02, 0x02, 0x02, 0x02, 0x00 }, // 0x6c, l 234 | { 0x07, 0x00, 0x00, 0x0a, 0x15, 0x15, 0x11, 0x11, 0x00 }, // 0x6d, m 235 | { 0x07, 0x00, 0x00, 0x16, 0x19, 0x11, 0x11, 0x11, 0x00 }, // 0x6e, n 236 | { 0x07, 0x00, 0x00, 0x0e, 0x11, 0x11, 0x11, 0x0e, 0x00 }, // 0x6f, o 237 | { 0x07, 0x00, 0x00, 0x1c, 0x12, 0x12, 0x1c, 0x10, 0x10 }, // 0x70, p 238 | { 0x07, 0x00, 0x00, 0x07, 0x09, 0x09, 0x07, 0x01, 0x01 }, // 0x71, q 239 | { 0x07, 0x00, 0x00, 0x16, 0x19, 0x10, 0x10, 0x10, 0x00 }, // 0x72, r 240 | { 0x07, 0x00, 0x00, 0x0f, 0x10, 0x0e, 0x01, 0x1e, 0x00 }, // 0x73, s 241 | { 0x07, 0x08, 0x08, 0x1c, 0x08, 0x08, 0x09, 0x06, 0x00 }, // 0x74, t 242 | { 0x07, 0x00, 0x00, 0x11, 0x11, 0x11, 0x13, 0x0d, 0x00 }, // 0x75, u 243 | { 0x07, 0x00, 0x00, 0x11, 0x11, 0x11, 0x0a, 0x04, 0x00 }, // 0x76, v 244 | { 0x07, 0x00, 0x00, 0x11, 0x11, 0x15, 0x15, 0x0a, 0x00 }, // 0x77, w 245 | { 0x07, 0x00, 0x00, 0x11, 0x0a, 0x04, 0x0a, 0x11, 0x00 }, // 0x78, x 246 | { 0x07, 0x00, 0x00, 0x11, 0x11, 0x0f, 0x01, 0x11, 0x0e }, // 0x79, y 247 | { 0x07, 0x00, 0x00, 0x1f, 0x02, 0x04, 0x08, 0x1f, 0x00 }, // 0x7a, z 248 | { 0x07, 0x06, 0x08, 0x08, 0x10, 0x08, 0x08, 0x06, 0x00 }, // 0x7b, { 249 | { 0x07, 0x04, 0x04, 0x04, 0x00, 0x04, 0x04, 0x04, 0x00 }, // 0x7c, | 250 | { 0x07, 0x0c, 0x02, 0x02, 0x01, 0x02, 0x02, 0x0c, 0x00 }, // 0x7d, } 251 | { 0x07, 0x08, 0x15, 0x02, 0x00, 0x00, 0x00, 0x00, 0x00 }, // 0x7e, ~ 252 | { 0x07, 0x1f, 0x1f, 0x1f, 0x1f, 0x1f, 0x1f, 0x1f, 0x00 } // 0x7f, DEL 253 | }; 254 | //************************************************************************************************** 255 | void connect_to_WiFi() { // We start by connecting to a WiFi network 256 | Serial.println(""); 257 | Serial.print("Connecting to "); 258 | Serial.println(ssid); 259 | 260 | WiFi.mode(WIFI_STA); 261 | WiFi.begin(ssid, pass); 262 | 263 | while (WiFi.status() != WL_CONNECTED) { 264 | delay(500); 265 | Serial.print("."); 266 | } 267 | Serial.println(""); 268 | 269 | Serial.println("WiFi connected"); 270 | Serial.print("IP address: "); 271 | Serial.println(String(WiFi.localIP())); 272 | Serial.println("Starting UDP"); 273 | udp.begin(localPort); 274 | Serial.print("Local port: "); 275 | Serial.println(udp.localPort()); 276 | } 277 | //************************************************************************************************** 278 | tm* connectNTP() { //if response from NTP was succesfull return *tm else return a nullpointer 279 | WiFi.hostByName(ntpServerName, timeServerIP); 280 | Serial.println(timeServerIP); 281 | Serial.println("sending NTP packet..."); 282 | // set all bytes in the buffer to 0 283 | memset(packetBuffer, 0, NTP_PACKET_SIZE); 284 | // Initialize values needed to form NTP request 285 | // (see URL above for details on the packets) 286 | packetBuffer[0] = 0b11100011; // LI, Version, Mode 287 | packetBuffer[1] = 0; // Stratum, or type of clock 288 | packetBuffer[2] = 6; // Polling Interval 289 | packetBuffer[3] = 0xEC; // Peer Clock Precision 290 | // 8 bytes of zero for Root Delay & Root Dispersion 291 | packetBuffer[12] = 49; 292 | packetBuffer[13] = 0x4E; 293 | packetBuffer[14] = 49; 294 | packetBuffer[15] = 52; 295 | // all NTP fields have been given values, now 296 | // you can send a packet requesting a timestamp: 297 | udp.beginPacket(timeServerIP, 123); //NTP requests are to port 123 298 | udp.write(packetBuffer, NTP_PACKET_SIZE); 299 | udp.endPacket(); 300 | delay(1000); // wait to see if a reply is available 301 | int cb = udp.parsePacket(); 302 | udp.read(packetBuffer, NTP_PACKET_SIZE); // read the packet into the buffer 303 | //the timestamp starts at byte 40 of the received packet and is four bytes, 304 | // or two words, long. First, esxtract the two words: 305 | unsigned long highWord = word(packetBuffer[40], packetBuffer[41]); 306 | unsigned long lowWord = word(packetBuffer[42], packetBuffer[43]); 307 | // combine the four bytes (two words) into a long integer 308 | // this is NTP time (seconds since Jan 1 1900): 309 | unsigned long secsSince1900 = highWord << 16 | lowWord; 310 | // now convert NTP time into everyday time: 311 | const unsigned long seventyYears = 2208988800UL; 312 | // subtract seventy years: 313 | epoch = secsSince1900 - seventyYears +2; //+2000ms Verarbeitungszeit 314 | epoch=epoch+3600*corectie; // difference -6h = -6* 3600 sec) 315 | time_t t; 316 | t = epoch; 317 | tm* tt; 318 | tt = localtime(&t); 319 | if (cb == 48) 320 | return (tt); 321 | else 322 | return (NULL); 323 | } 324 | //************************************************************************************************** 325 | void rtc_init(unsigned char sda, unsigned char scl) { 326 | Wire.begin(sda, scl); 327 | rtc_Write(controlREG, 0x00); 328 | } 329 | //************************************************************************************************** 330 | // BCD Code 331 | //************************************************************************************************** 332 | unsigned char dec2bcd(unsigned char x) { //value 0...99 333 | unsigned char z, e, r; 334 | e = x % 10; 335 | z = x / 10; 336 | z = z << 4; 337 | r = e | z; 338 | return (r); 339 | } 340 | unsigned char bcd2dec(unsigned char x) { //value 0...99 341 | int z, e; 342 | e = x & 0x0F; 343 | z = x & 0xF0; 344 | z = z >> 4; 345 | z = z * 10; 346 | return (z + e); 347 | } 348 | //************************************************************************************************** 349 | // RTC I2C Code 350 | //************************************************************************************************** 351 | unsigned char rtc_Read(unsigned char regaddress) { 352 | Wire.beginTransmission(DS3231_ADDRESS); 353 | Wire.write(regaddress); 354 | Wire.endTransmission(); 355 | Wire.requestFrom((unsigned char) DS3231_ADDRESS, (unsigned char) 1); 356 | return (Wire.read()); 357 | } 358 | void rtc_Write(unsigned char regaddress, unsigned char value) { 359 | Wire.beginTransmission(DS3231_ADDRESS); 360 | Wire.write(regaddress); 361 | Wire.write(value); 362 | Wire.endTransmission(); 363 | } 364 | //************************************************************************************************** 365 | unsigned char rtc_sekunde() { 366 | return (bcd2dec(rtc_Read(secondREG))); 367 | } 368 | unsigned char rtc_minute() { 369 | return (bcd2dec(rtc_Read(minuteREG))); 370 | } 371 | unsigned char rtc_stunde() { 372 | return (bcd2dec(rtc_Read(hourREG))); 373 | } 374 | unsigned char rtc_wochentag() { 375 | return (bcd2dec(rtc_Read(WTREG))); 376 | } 377 | unsigned char rtc_tag() { 378 | return (bcd2dec(rtc_Read(dateREG))); 379 | } 380 | unsigned char rtc_monat() { 381 | return (bcd2dec(rtc_Read(monthREG))); 382 | } 383 | unsigned char rtc_jahr() { 384 | return (bcd2dec(rtc_Read(yearREG))); 385 | } 386 | void rtc_sekunde(unsigned char sek) { 387 | rtc_Write(secondREG, (dec2bcd(sek))); 388 | } 389 | void rtc_minute(unsigned char min) { 390 | rtc_Write(minuteREG, (dec2bcd(min))); 391 | } 392 | void rtc_stunde(unsigned char std) { 393 | rtc_Write(hourREG, (dec2bcd(std))); 394 | } 395 | void rtc_wochentag(unsigned char wt) { 396 | rtc_Write(WTREG, (dec2bcd(wt))); 397 | } 398 | void rtc_tag(unsigned char tag) { 399 | rtc_Write(dateREG, (dec2bcd(tag))); 400 | } 401 | void rtc_monat(unsigned char mon) { 402 | rtc_Write(monthREG, (dec2bcd(mon))); 403 | } 404 | void rtc_jahr(unsigned char jahr) { 405 | rtc_Write(yearREG, (dec2bcd(jahr))); 406 | } 407 | //************************************************************************************************** 408 | void rtc_set(tm* tt) { 409 | rtc_sekunde((unsigned char) tt->tm_sec); 410 | rtc_minute((unsigned char) tt->tm_min); 411 | rtc_stunde((unsigned char) tt->tm_hour); 412 | rtc_tag((unsigned char) tt->tm_mday); 413 | rtc_monat((unsigned char) tt->tm_mon + 1); 414 | rtc_jahr((unsigned char) tt->tm_year - 100); 415 | rtc_wochentag((unsigned char) tt->tm_wday); 416 | } 417 | //************************************************************************************************** 418 | float rtc_temp() { 419 | float t = 0.0; 420 | unsigned char lowByte = 0; 421 | signed char highByte = 0; 422 | lowByte = rtc_Read(tempLSBREG); 423 | highByte = rtc_Read(tempMSBREG); 424 | lowByte >>= 6; 425 | lowByte &= 0x03; 426 | t = ((float) lowByte); 427 | t *= 0.25; 428 | t += highByte; 429 | return (t); // return temp value 430 | } 431 | //************************************************************************************************** 432 | void rtc2mez() { 433 | 434 | unsigned short JaZiff; //Jahresziffer 435 | unsigned short JhZiff = 6; //Jahrhundertziffer für 20.Jahrhundert 436 | unsigned short TaZiff; //Tagesziffer 437 | unsigned short WoTag; //Wochentag 438 | unsigned short SJK = 0; //Schaltjahreskorrektur 439 | unsigned short ZDiff; //Zeitdifferenz UTC MEZ/MESZ 440 | unsigned short MoZiff[12] = { 0, 3, 3, 6, 1, 4, 6, 2, 5, 0, 3, 5 }; //Monatsziffer 441 | unsigned short Tage_Monat[12] = { 31, 28, 31, 30, 31, 30, 31, 31, 30, 31, 30, 442 | 31 }; 443 | unsigned short Jahr, Tag, Monat, Stunde, Minute, Sekunde; 444 | //RTC_setMonat(3); 445 | Jahr = rtc_jahr(); 446 | if (Jahr > 99) 447 | Jahr = 0; 448 | Monat = rtc_monat(); 449 | if (Monat > 12) 450 | Monat = 0; 451 | Tag = rtc_tag(); 452 | if (Tag > 31) 453 | Tag = 0; 454 | Stunde = rtc_stunde(); 455 | if (Stunde > 23) 456 | Stunde = 0; 457 | Minute = rtc_minute(); 458 | if (Minute > 59) 459 | Minute = 0; 460 | Sekunde = rtc_sekunde(); 461 | if (Sekunde > 59) 462 | Sekunde = 0; 463 | 464 | JaZiff = ((Jahr + Jahr / 4) % 7); 465 | TaZiff = (Tag % 7); 466 | if ((Jahr % 4) == 0) //Schaltjahr ? 467 | { 468 | Tage_Monat[1] = 29; //dann hat der Febr 29 Tage 469 | if (Monat < 3) 470 | SJK = 6; 471 | else 472 | SJK = 0; 473 | } 474 | WoTag = ((TaZiff + MoZiff[Monat - 1] + JhZiff + JaZiff + SJK) % 7); 475 | 476 | if (Monat < 3 || Monat > 10) 477 | ZDiff = 1; // keine Sommerzeit in Jan, Feb, Nov, Dez 478 | if (Monat > 3 && Monat < 10) 479 | ZDiff = 2; // Sommerz. in Apr, Mai, Jun, Jul, Aug, Sep 480 | if (Monat == 3) { 481 | ZDiff = 1; 482 | if (Tag > 24) //Sommerzeit ab letzten Sonntag des Monats 483 | { 484 | if (Tag == 25) { 485 | if ((Tag + WoTag) < 26) 486 | ZDiff = 2; 487 | } 488 | if (Tag == 26) { 489 | if ((Tag + WoTag) < 28) 490 | ZDiff = 2; 491 | } 492 | if (Tag == 27) { 493 | if ((Tag + WoTag) < 30) 494 | ZDiff = 2; 495 | } 496 | if (Tag == 28) { 497 | if ((Tag + WoTag) < 32) 498 | ZDiff = 2; 499 | } 500 | if (Tag == 29) { 501 | if ((Tag + WoTag) < 34) 502 | ZDiff = 2; 503 | } 504 | if (Tag == 30) { 505 | if ((Tag + WoTag) < 36) 506 | ZDiff = 2; 507 | } 508 | if (Tag == 31) { 509 | if ((Tag + WoTag) < 38) 510 | ZDiff = 2; 511 | } 512 | if ((ZDiff == 2) && (Stunde + 1 < 2) && (WoTag == 0)) 513 | ZDiff = 1; //erst ab 02 Uhr 514 | } 515 | } 516 | if (Monat == 10) { 517 | ZDiff = 2; 518 | if (Tag > 24) //Sommerzeit ab letzten Sonntag des Monats 519 | { 520 | if (Tag == 25) { 521 | if ((Tag + WoTag) < 26) 522 | ZDiff = 1; 523 | } 524 | if (Tag == 26) { 525 | if ((Tag + WoTag) < 28) 526 | ZDiff = 1; 527 | } 528 | if (Tag == 27) { 529 | if ((Tag + WoTag) < 30) 530 | ZDiff = 1; 531 | } 532 | if (Tag == 28) { 533 | if ((Tag + WoTag) < 32) 534 | ZDiff = 1; 535 | } 536 | if (Tag == 29) { 537 | if ((Tag + WoTag) < 34) 538 | ZDiff = 1; 539 | } 540 | if (Tag == 30) { 541 | if ((Tag + WoTag) < 36) 542 | ZDiff = 1; 543 | } 544 | if (Tag == 31) { 545 | if ((Tag + WoTag) < 38) 546 | ZDiff = 1; 547 | } 548 | if ((ZDiff == 1) && (Stunde == 0) && (WoTag == 0)) 549 | ZDiff = 2; //erst ab 02 Uhr 550 | } 551 | } 552 | Stunde = Stunde + ZDiff; 553 | if (Stunde > 23) //Tageskorrektur 554 | { 555 | Stunde = Stunde - 24; //kann 0 oder 1 sein 556 | Tag = Tag + 1; 557 | WoTag = WoTag + 1; 558 | if (Tag > Tage_Monat[Monat - 1]) { 559 | Tag = 1; 560 | Monat = Monat + 1; 561 | if (Monat > 12) { 562 | Monat = 1; 563 | Jahr = Jahr + 1; 564 | } 565 | } 566 | } 567 | MEZ.WT = WoTag; //So=0, Mo=1, Di=2 ... 568 | MEZ.sek1 = Sekunde % 10; 569 | MEZ.sek2 = Sekunde / 10; 570 | MEZ.sek12 = Sekunde; 571 | MEZ.min1 = Minute % 10; 572 | MEZ.min2 = Minute / 10; 573 | MEZ.min12 = Minute; 574 | MEZ.std1 = Stunde % 10; 575 | MEZ.std2 = Stunde / 10; 576 | MEZ.std12 = Stunde; 577 | MEZ.tag12 = Tag; 578 | MEZ.tag1 = Tag % 10; 579 | MEZ.tag2 = Tag / 10; 580 | MEZ.mon12 = Monat; 581 | MEZ.mon1 = Monat % 10; 582 | MEZ.mon2 = Monat / 10; 583 | MEZ.jahr12 = Jahr; 584 | MEZ.jahr1 = Jahr % 10; 585 | MEZ.jahr2 = Jahr / 10; 586 | } 587 | 588 | //************************************************************************************************* 589 | const unsigned short InitArr[7][2] = { { 0x0C, 0x00 }, // display off 590 | { 0x00, 0xFF }, // no LEDtest 591 | { 0x09, 0x00 }, // BCD off 592 | { 0x0F, 0x00 }, // normal operation 593 | { 0x0B, 0x07 }, // start display 594 | { 0x0A, 0x04 }, // brightness 595 | { 0x0C, 0x01 } // display on 596 | }; 597 | //************************************************************************************************** 598 | void max7219_init() //all MAX7219 init 599 | { 600 | unsigned short i, j; 601 | for (i = 0; i < 7; i++) { 602 | digitalWrite(CS, LOW); 603 | delayMicroseconds(1); 604 | for (j = 0; j < anzMAX; j++) { 605 | SPI.write(InitArr[i][0]); //register 606 | SPI.write(InitArr[i][1]); //value 607 | } 608 | digitalWrite(CS, HIGH); 609 | } 610 | } 611 | //************************************************************************************************** 612 | void max7219_set_brightness(unsigned short br) //brightness MAX7219 613 | { 614 | unsigned short j; 615 | if (br < 16) { 616 | digitalWrite(CS, LOW); 617 | delayMicroseconds(1); 618 | for (j = 0; j < anzMAX; j++) { 619 | SPI.write(0x0A); //register 620 | SPI.write(br); //value 621 | } 622 | digitalWrite(CS, HIGH); 623 | } 624 | } 625 | //************************************************************************************************** 626 | void helpArr_init(void) //helperarray init 627 | { 628 | unsigned short i, j, k; 629 | j = 0; 630 | k = 0; 631 | for (i = 0; i < anzMAX * 8; i++) { 632 | helpArrPos[i] = (1 << j); //bitmask 633 | helpArrMAX[i] = k; 634 | j++; 635 | if (j > 7) { 636 | j = 0; 637 | k++; 638 | } 639 | } 640 | } 641 | //************************************************************************************************** 642 | void clear_Display() //clear all 643 | { 644 | unsigned short i, j; 645 | for (i = 0; i < 8; i++) //8 rows 646 | { 647 | digitalWrite(CS, LOW); 648 | delayMicroseconds(1); 649 | for (j = anzMAX; j > 0; j--) { 650 | LEDarr[j - 1][i] = 0; //LEDarr clear 651 | SPI.write(i + 1); //current row 652 | SPI.write(LEDarr[j - 1][i]); 653 | } 654 | digitalWrite(CS, HIGH); 655 | } 656 | } 657 | //********************************************************************************************************* 658 | void rotate_90() // for Generic displays 659 | { 660 | for (uint8_t k = anzMAX; k > 0; k--) { 661 | 662 | uint8_t i, j, m, imask, jmask; 663 | uint8_t tmp[8]={0,0,0,0,0,0,0,0}; 664 | for ( i = 0, imask = 0x01; i < 8; i++, imask <<= 1) { 665 | for (j = 0, jmask = 0x01; j < 8; j++, jmask <<= 1) { 666 | if (LEDarr[k-1][i] & jmask) { 667 | tmp[j] |= imask; 668 | } 669 | } 670 | } 671 | for(m=0; m<8; m++){ 672 | LEDarr[k-1][m]=tmp[m]; 673 | } 674 | } 675 | } 676 | //************************************************************************************************** 677 | void refresh_display() //take info into LEDarr 678 | { 679 | unsigned short i, j; 680 | 681 | #ifdef ROTATE_90 682 | rotate_90(); 683 | #endif 684 | 685 | for (i = 0; i < 8; i++) //8 rows 686 | { 687 | digitalWrite(CS, LOW); 688 | delayMicroseconds(1); 689 | for (j = anzMAX; j > 0; j--) { 690 | SPI.write(i + 1); //current row 691 | 692 | #ifdef REVERSE_HORIZONTAL 693 | SPI.setBitOrder(LSBFIRST); // bitorder for reverse columns 694 | #endif 695 | 696 | #ifdef REVERSE_VERTICAL 697 | SPI.write(LEDarr[j - 1][7-i]); 698 | #else 699 | SPI.write(LEDarr[j - 1][i]); 700 | #endif 701 | 702 | #ifdef REVERSE_HORIZONTAL 703 | SPI.setBitOrder(MSBFIRST); // reset bitorder 704 | #endif 705 | } 706 | digitalWrite(CS, HIGH); 707 | } 708 | } 709 | //************************************************************************************************** 710 | void char2Arr(unsigned short ch, int PosX, short PosY) { //characters into arr 711 | int i, j, k, l, m, o1, o2, o3, o4; //in LEDarr 712 | PosX++; 713 | k = ch - 32; //ASCII position in font 714 | if ((k >= 0) && (k < 96)) //character found in font? 715 | { 716 | o4 = font1[k][0]; //character width 717 | o3 = 1 << (o4 - 2); 718 | for (i = 0; i < o4; i++) { 719 | if (((PosX - i <= maxPosX) && (PosX - i >= 0)) 720 | && ((PosY > -8) && (PosY < 8))) //within matrix? 721 | { 722 | o1 = helpArrPos[PosX - i]; 723 | o2 = helpArrMAX[PosX - i]; 724 | for (j = 0; j < 8; j++) { 725 | if (((PosY >= 0) && (PosY <= j)) || ((PosY < 0) && (j < PosY + 8))) //scroll vertical 726 | { 727 | l = font1[k][j + 1]; 728 | m = (l & (o3 >> i)); //e.g. o4=7 0zzzzz0, o4=4 0zz0 729 | if (m > 0) 730 | LEDarr[o2][j - PosY] = LEDarr[o2][j - PosY] | (o1); //set point 731 | else 732 | LEDarr[o2][j - PosY] = LEDarr[o2][j - PosY] & (~o1); //clear point 733 | } 734 | } 735 | } 736 | } 737 | } 738 | } 739 | 740 | //************************************************************************************************** 741 | void timer50ms() { 742 | static unsigned int cnt50ms = 0; 743 | static unsigned int cnt1s = 0; 744 | static unsigned int cnt1h = 0; 745 | f_tckr50ms = true; 746 | cnt50ms++; 747 | if (cnt50ms == 20) { 748 | f_tckr1s = true; // 1 sec 749 | cnt1s++; 750 | cnt50ms = 0; 751 | } 752 | if (cnt1s == 3600) { // 1h 753 | cnt1h++; 754 | cnt1s = 0; 755 | } 756 | if (cnt1h == 24) { // 1d 757 | f_tckr24h = true; 758 | cnt1h = 0; 759 | } 760 | } 761 | //************************************************************************************************** 762 | // 763 | //The setup function is called once at startup of the sketch 764 | void setup() { 765 | // Add your initialization code here 766 | pinMode(CS, OUTPUT); 767 | digitalWrite(CS, HIGH); 768 | Serial.begin(115200); 769 | dht.begin(); 770 | temperatura = dht.readTemperature(); 771 | umiditate = dht.readHumidity(); 772 | Serial.print(temperatura); 773 | Serial.println("gr.Celsius"); 774 | //rtc.init(SDA, SCL); 775 | SPI.begin(); 776 | helpArr_init(); 777 | max7219_init(); 778 | max7219_set_brightness(0); 779 | rtc_init(SDA, SCL); 780 | clear_Display(); 781 | tckr.attach(0.05, timer50ms); // every 50 msec 782 | connect_to_WiFi(); 783 | tm* tt; 784 | tt = connectNTP(); 785 | if (tt != NULL) 786 | rtc_set(tt); 787 | else 788 | Serial.println("no timepacket received"); 789 | } 790 | //************************************************************************************************** 791 | // The loop function is called in an endless loop 792 | void loop() { 793 | //Add your repeated code here 794 | unsigned int sek1 = 0, sek2 = 0, min1 = 0, min2 = 0, std1 = 0, std2 = 0; 795 | unsigned int sek11 = 0, sek12 = 0, sek21 = 0, sek22 = 0; 796 | unsigned int min11 = 0, min12 = 0, min21 = 0, min22 = 0; 797 | unsigned int std11 = 0, std12 = 0, std21 = 0, std22 = 0; 798 | signed int x = 0; //x1,x2; 799 | signed int y = 0, y1 = 0, y2 = 0; 800 | bool updown = false; 801 | unsigned int sc1 = 0, sc2 = 0, sc3 = 0, sc4 = 0, sc5 = 0, sc6 = 0; 802 | bool f_scrollend_y = false; 803 | unsigned int f_scroll_x = false; 804 | 805 | // temperatura = random(-20,25); 806 | // umiditate = random(1,55); 807 | 808 | 809 | z_PosX = maxPosX; 810 | d_PosX = -8; 811 | // x=0; x1=0; x2=0; 812 | 813 | refresh_display(); 814 | updown = true; 815 | if (updown == false) { 816 | y2 = -9; 817 | y1 = 8; 818 | } 819 | if (updown == true) { //scroll up to down 820 | y2 = 8; 821 | y1 = -8; 822 | } 823 | while (true) { 824 | yield(); 825 | if (f_tckr24h == true) { //syncronisize RTC every day 826 | f_tckr24h = false; 827 | tm* tt; 828 | tt = connectNTP(); 829 | if (tt != NULL) 830 | rtc_set(tt); 831 | else 832 | Serial.println("no timepacket received"); 833 | } 834 | if (f_tckr1s == true) // flag 1sek 835 | { 836 | rtc2mez(); 837 | sek1 = MEZ.sek1; 838 | sek2 = MEZ.sek2; 839 | min1 = MEZ.min1; 840 | min2 = MEZ.min2; 841 | std1 = MEZ.std1; 842 | std2 = MEZ.std2; 843 | y = y2; //scroll updown 844 | sc1 = 1; 845 | sek1++; 846 | if (sek1 == 10) { 847 | sc2 = 1; 848 | sek2++; 849 | sek1 = 0; 850 | } 851 | if (sek2 == 6) { 852 | min1++; 853 | sek2 = 0; 854 | sc3 = 1; 855 | } 856 | if (min1 == 10) { 857 | min2++; 858 | min1 = 0; 859 | sc4 = 1; 860 | } 861 | if (min2 == 6) { 862 | std1++; 863 | min2 = 0; 864 | sc5 = 1; 865 | } 866 | if (std1 == 10) { 867 | std2++; 868 | std1 = 0; 869 | sc6 = 1; 870 | } 871 | if ((std2 == 2) && (std1 == 4)) { 872 | std1 = 0; 873 | std2 = 0; 874 | sc6 = 1; 875 | } 876 | 877 | sek11 = sek12; 878 | sek12 = sek1; 879 | sek21 = sek22; 880 | sek22 = sek2; 881 | min11 = min12; 882 | min12 = min1; 883 | min21 = min22; 884 | min22 = min2; 885 | std11 = std12; 886 | std12 = std1; 887 | std21 = std22; 888 | std22 = std2; 889 | f_tckr1s = false; 890 | if (MEZ.sek12 == 35) 891 | f_scroll_x = true; 892 | if (MEZ.sek12 == 59) 893 | { 894 | temperatura = dht.readTemperature(); 895 | Serial.print("t = "); 896 | Serial.print(temperatura); 897 | Serial.print("gr.C h = "); 898 | umiditate = dht.readHumidity(); 899 | Serial.print(umiditate); 900 | Serial.println("%rh"); 901 | if (temperatura < 0) 902 | { 903 | temp = -10*temperatura; 904 | minus = 1; 905 | } 906 | else 907 | { 908 | minus = 0; 909 | temp = 10*temperatura; 910 | } 911 | tempz = temp/100; 912 | tempr = temp - 100*tempz; 913 | tempu = tempr/10; 914 | temps = tempr%10; 915 | } 916 | } // end 1s 917 | if (f_tckr50ms == true) { 918 | f_tckr50ms = false; 919 | if (f_scroll_x == true) { 920 | z_PosX++; 921 | d_PosX++; 922 | if (d_PosX == mult) 923 | z_PosX = 0; 924 | if (z_PosX == maxPosX) { 925 | f_scroll_x = false; 926 | d_PosX = -8; 927 | } 928 | } 929 | if (sc1 == 1) { 930 | if (updown == 1) 931 | y--; 932 | else 933 | y++; 934 | char2Arr(48 + sek12, z_PosX - 42, y); 935 | char2Arr(48 + sek11, z_PosX - 42, y + y1); 936 | if (y == 0) { 937 | sc1 = 0; 938 | f_scrollend_y = true; 939 | } 940 | } 941 | else 942 | char2Arr(48 + sek1, z_PosX - 42, 0); 943 | 944 | if (sc2 == 1) { 945 | char2Arr(48 + sek22, z_PosX - 36, y); 946 | char2Arr(48 + sek21, z_PosX - 36, y + y1); 947 | if (y == 0) 948 | sc2 = 0; 949 | } 950 | else 951 | char2Arr(48 + sek2, z_PosX - 36, 0); 952 | 953 | char2Arr(':', z_PosX - 32, 0); 954 | 955 | if (sc3 == 1) { 956 | char2Arr(48 + min12, z_PosX - 25, y); 957 | char2Arr(48 + min11, z_PosX - 25, y + y1); 958 | if (y == 0) 959 | sc3 = 0; 960 | } 961 | else 962 | char2Arr(48 + min1, z_PosX - 25, 0); 963 | 964 | if (sc4 == 1) { 965 | char2Arr(48 + min22, z_PosX - 19, y); 966 | char2Arr(48 + min21, z_PosX - 19, y + y1); 967 | if (y == 0) 968 | sc4 = 0; 969 | } 970 | else 971 | char2Arr(48 + min2, z_PosX - 19, 0); 972 | 973 | char2Arr(':', z_PosX - 15 + x, 0); 974 | 975 | if (sc5 == 1) { 976 | char2Arr(48 + std12, z_PosX - 8, y); 977 | char2Arr(48 + std11, z_PosX - 8, y + y1); 978 | if (y == 0) 979 | sc5 = 0; 980 | } 981 | else 982 | char2Arr(48 + std1, z_PosX - 8, 0); 983 | 984 | if (sc6 == 1) { 985 | char2Arr(48 + std22, z_PosX - 2, y); 986 | char2Arr(48 + std21, z_PosX - 2, y + y1); 987 | if (y == 0) 988 | sc6 = 0; 989 | } 990 | else 991 | char2Arr(48 + std2, z_PosX - 2, 0); 992 | 993 | char2Arr(' ', d_PosX+7, 0); 994 | char2Arr(' ', d_PosX+1, 0); 995 | char2Arr(' ', d_PosX-5, 0); 996 | poz = 11; 997 | char2Arr(WT_arr[MEZ.WT][0], d_PosX - poz, 0); //day of the week 998 | poz = poz+6; 999 | char2Arr(WT_arr[MEZ.WT][1], d_PosX - poz, 0); 1000 | poz = poz+6; 1001 | char2Arr(WT_arr[MEZ.WT][2], d_PosX - poz, 0); 1002 | poz = poz+6; 1003 | char2Arr(WT_arr[MEZ.WT][3], d_PosX - poz, 0); 1004 | poz = poz+6; 1005 | char2Arr(' ', d_PosX - poz, 0); 1006 | poz = poz+6; 1007 | char2Arr(48 + MEZ.tag2, d_PosX - poz, 0); //day 1008 | poz = poz+6; 1009 | char2Arr(48 + MEZ.tag1, d_PosX - poz, 0); 1010 | poz = poz+6; 1011 | char2Arr(' ', d_PosX - poz, 0); 1012 | char2Arr('.', d_PosX - poz, 0); 1013 | poz = poz+6; 1014 | 1015 | char2Arr(M_arr[MEZ.mon12 - 1][1], d_PosX - poz, 0); 1016 | poz = poz+6; 1017 | char2Arr(M_arr[MEZ.mon12 - 1][2], d_PosX - poz, 0); 1018 | poz = poz+6; 1019 | char2Arr(M_arr[MEZ.mon12 - 1][3], d_PosX - poz, 0); 1020 | poz = poz+6; 1021 | char2Arr(' ', d_PosX - poz, 0); 1022 | char2Arr('.', d_PosX - poz, 0); 1023 | poz = poz+6; 1024 | char2Arr('2', d_PosX - poz, 0); //year 1025 | poz = poz+6; 1026 | char2Arr('0', d_PosX - poz, 0); 1027 | poz = poz+6; 1028 | char2Arr(48 + MEZ.jahr2, d_PosX - poz, 0); 1029 | poz = poz+6; 1030 | char2Arr(48 + MEZ.jahr1, d_PosX - poz, 0); 1031 | poz = poz+6; 1032 | char2Arr(' ', d_PosX - poz, 0); 1033 | poz = poz+6; 1034 | char2Arr(' ', d_PosX - poz, 0); 1035 | poz = poz+6; 1036 | char2Arr(' ', d_PosX - poz, 0); 1037 | poz = poz+6; 1038 | 1039 | // my part (niq_ro part) 1040 | if (minus == 1) 1041 | char2Arr('-', d_PosX - poz, 0); 1042 | else 1043 | char2Arr('+', d_PosX - poz, 0); 1044 | poz = poz+6; 1045 | 1046 | if (tempz > 0) 1047 | { 1048 | char2Arr(48+tempz, d_PosX - poz, 0); 1049 | poz = poz+6; 1050 | } 1051 | char2Arr(48+tempu, d_PosX - poz, 0); 1052 | poz = poz+6; 1053 | 1054 | char2Arr(' ', d_PosX - poz, 0); 1055 | char2Arr('.', d_PosX - poz, 0); 1056 | poz = poz+6; 1057 | 1058 | char2Arr(48+temps, d_PosX - poz, 0); 1059 | poz = poz+6; 1060 | char2Arr('$', d_PosX - poz, 0); 1061 | poz = poz+6; 1062 | char2Arr('C', d_PosX - poz, 0); 1063 | poz = poz+6; 1064 | 1065 | char2Arr(' ', d_PosX - poz, 0); 1066 | poz = poz+6; 1067 | char2Arr(' ', d_PosX - poz, 0); 1068 | poz = poz+6; 1069 | 1070 | if (umiditate >= 10) 1071 | { 1072 | char2Arr(48 + (umiditate / 10), d_PosX - poz, 0); 1073 | poz = poz+6; 1074 | } 1075 | 1076 | char2Arr(48 + (umiditate%10), d_PosX - poz, 0); 1077 | poz = poz+6; 1078 | char2Arr('%', d_PosX - poz, 0); 1079 | poz = poz+6; 1080 | char2Arr('R', d_PosX - poz, 0); 1081 | poz = poz+6; 1082 | char2Arr('H', d_PosX - poz, 0); 1083 | // } 1084 | poz = poz+6; 1085 | char2Arr(' ', d_PosX - poz, 0); 1086 | poz = poz+6; 1087 | char2Arr(' ', d_PosX - poz, 0); 1088 | poz = poz+6; 1089 | char2Arr(' ', d_PosX - poz, 0); 1090 | //poz = poz+6; 1091 | mult = poz + 5; 1092 | 1093 | // end Seby & my part 1094 | 1095 | refresh_display(); //alle 50ms 1096 | if (f_scrollend_y == true) { 1097 | f_scrollend_y = false; 1098 | } 1099 | } //end 50ms 1100 | if (y == 0) { 1101 | // do something else 1102 | } 1103 | } //end while(true) 1104 | //this section can not be reached 1105 | } 1106 | -------------------------------------------------------------------------------- /MatrixClock_ESP8266_DHT.ino: -------------------------------------------------------------------------------- 1 | //********************************************************************************************************* 2 | //* ESP8266 MatrixClock by Wolle / schreibfaul1 * 3 | //********************************************************************************************************* 4 | // 5 | // first release on 26.02.2017 6 | // updated on 26.03.2019 7 | // Version 1.2.1 8 | // https://github.com/schreibfaul1/ESP8266-LED-Matrix-Clock 9 | // 10 | // THE SOFTWARE IS PROVIDED "AS IS" FOR PRIVATE USE ONLY, IT IS NOT FOR COMMERCIAL USE IN WHOLE OR PART OR CONCEPT. 11 | // FOR PERSONAL USE IT IS SUPPLIED WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE 12 | // WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHOR 13 | // OR COPYRIGHT HOLDER BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR 14 | // OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE 15 | // 16 | // 17 | // small changes by Nicu FLORICA (niq_ro), 31-May_2019 18 | // add DHT sensor for temperature and humidity 19 | 20 | #include 21 | #include 22 | #include 23 | #include 24 | #include 25 | #include 26 | #include 27 | #include "DHT.h" 28 | 29 | 30 | 31 | 32 | #define SDA 5 // Pin sda (I2C) 33 | #define SCL 4 // Pin scl (I2C) 34 | #define CS 15 // Pin cs (SPI) 35 | #define anzMAX 6 // Anzahl der kaskadierten Module 36 | 37 | char ssid[] = "networkname"; // your network SSID (name) 38 | char pass[] = "password"; // your network password 39 | 40 | // other displays ------------------------------------- 41 | #define REVERSE_HORIZONTAL // Parola, Generic and IC-Station 42 | //#define REVERSE_VERTICAL // IC-Station display 43 | #define ROTATE_90 // Generic display 44 | /* 45 | p A B C D E F G 7 6 5 4 3 2 1 0 G F E D C B A p G F E D C B A p 46 | ------------------------ ------------------------ ------------------------ ------------------------ 47 | 0 |o o o o o o o o| p |o o o o o o o o| 0 |o o o o o o o o| 7 |o o o o o o o o| 48 | 1 |o o o o o o o o| A |o o o o o o o o| 1 |o o o o o o o o| 6 |o o o o o o o o| 49 | 2 |o o o o o o o o| B |o o o o o o o o| 2 |o o o o o o o o| 5 |o o o o o o o o| 50 | 3 |o o o o| C |o o o o| 3 |o o o o| 4 |o o o o| 51 | 4 |o o FC-16 o o| D |o o Generic o o| 4 |o o Parola o o| 3 |o o IC-Station o o| 52 | 5 |o o o o| E |o o o o| 5 |o o o o| 2 |o o o o| 53 | 6 |o o o o o o o o| F |o o o o o o o o| 6 |o o o o o o o o| 1 |o o o o o o o o| 54 | 7 |o o o o o o o o| G |o o o o o o o o| 7 |o o o o o o o o| 0 |o o o o o o o o| 55 | ------------------------ ------------------------ ------------------------ ------------------------ 56 | */ 57 | 58 | // DHT sensor 59 | #define DHTPIN 12 // what pin we're connected to // GPIO 13 = D6 60 | // Uncomment whatever type you're using! 61 | //#define DHTTYPE DHT11 // DHT 11 62 | #define DHTTYPE DHT22 // DHT 22 (AM2302) 63 | //#define DHTTYPE DHT21 // DHT 21 (AM2301) 64 | // Connect pin 1 (on the left) of the sensor to +5V 65 | // NOTE: If using a board with 3.3V logic like an Arduino Due connect pin 1 66 | // to 3.3V instead of 5V! 67 | // Connect pin 2 of the sensor to whatever your DHTPIN is 68 | // Connect pin 4 (on the right) of the sensor to GROUND 69 | // Connect a 10K resistor from pin 2 (data) to pin 1 (power) of the sensor 70 | // Initialize DHT sensor for normal 16mhz Arduino 71 | //DHT dht(DHTPIN, DHTTYPE); 72 | // NOTE: For working with a faster chip, like an Arduino Due or Teensy, you 73 | // might need to increase the threshold for cycle counts considered a 1 or 0. 74 | // You can do this by passing a 3rd parameter for this threshold. It's a bit 75 | // of fiddling to find the right value, but in general the faster the CPU the 76 | // higher the value. The default for a 16mhz AVR is a value of 6. For an 77 | // Arduino Due that runs at 84mhz a value of 30 works. 78 | // Example to initialize DHT sensor for Arduino Due: 79 | DHT dht(DHTPIN, DHTTYPE, 11); // for ESP8266 80 | 81 | 82 | unsigned short maxPosX = anzMAX * 8 - 1; //calculated maxposition 83 | unsigned short LEDarr[anzMAX][8]; //character matrix to display (40*8) 84 | unsigned short helpArrMAX[anzMAX * 8]; //helperarray for chardecoding 85 | unsigned short helpArrPos[anzMAX * 8]; //helperarray pos of chardecoding 86 | unsigned int z_PosX = 0; //xPosition im Display für Zeitanzeige 87 | unsigned int d_PosX = 0; //xPosition im Display f�r Datumanzeige 88 | bool f_tckr1s = false; 89 | bool f_tckr50ms = false; 90 | bool f_tckr24h = false; 91 | unsigned long epoch = 0; 92 | unsigned int localPort = 2390; // local port to listen for UDP packets 93 | const char* ntpServerName = "time.nist.gov"; 94 | const int NTP_PACKET_SIZE = 48; // NTP time stamp is in the first 48 bytes of the message 95 | byte packetBuffer[NTP_PACKET_SIZE]; //buffer to hold incoming and outgoing packets 96 | IPAddress timeServerIP; // time.nist.gov NTP server address 97 | tm *tt, ttm; 98 | #define corectie +1 99 | 100 | int temperatura = 0; 101 | int umiditate = 0; 102 | int poz, poz2; 103 | int mult = 224; 104 | 105 | //Variablen für RTC DS3231 106 | const unsigned char DS3231_ADDRESS = 0x68; 107 | const unsigned char secondREG = 0x00; 108 | const unsigned char minuteREG = 0x01; 109 | const unsigned char hourREG = 0x02; 110 | const unsigned char WTREG = 0x03; //weekday 111 | const unsigned char dateREG = 0x04; 112 | const unsigned char monthREG = 0x05; 113 | const unsigned char yearREG = 0x06; 114 | const unsigned char alarm_min1secREG = 0x07; 115 | const unsigned char alarm_min1minREG = 0x08; 116 | const unsigned char alarm_min1hrREG = 0x09; 117 | const unsigned char alarm_min1dateREG = 0x0A; 118 | const unsigned char alarm_min2minREG = 0x0B; 119 | const unsigned char alarm_min2hrREG = 0x0C; 120 | const unsigned char alarm_min2dateREG = 0x0D; 121 | const unsigned char controlREG = 0x0E; 122 | const unsigned char statusREG = 0x0F; 123 | const unsigned char ageoffsetREG = 0x10; 124 | const unsigned char tempMSBREG = 0x11; 125 | const unsigned char tempLSBREG = 0x12; 126 | const unsigned char _24_hour_format = 0; 127 | const unsigned char _12_hour_format = 1; 128 | const unsigned char AM = 0; 129 | const unsigned char PM = 1; 130 | 131 | struct DateTime { 132 | unsigned short sek1, sek2, sek12, min1, min2, min12, std1, std2, std12; 133 | unsigned short tag1, tag2, tag12, mon1, mon2, mon12, jahr1, jahr2, jahr12, WT; 134 | } MEZ; 135 | 136 | 137 | // The object for the Ticker 138 | Ticker tckr; 139 | // A UDP instance to let us send and receive packets over UDP 140 | WiFiUDP udp; 141 | 142 | 143 | //months 144 | char M_arr[12][5] = { { ' ', 'J', 'a', 'n', ' ' }, { ' ', 'F', 'e', 'b', ' ' }, 145 | { ' ', 'M', 'a', 'r', ' ' }, { ' ', 'A', 'p', 'r', ' ' }, { ' ', 'M', 'a', 146 | 'y', ' ' }, { ' ', 'J', 'u', 'n', 'e' }, { ' ', 'J', 'u', 'l', 'y' }, { 147 | ' ', 'A', 'u', 'g', ' ' }, { ' ', 'S', 'e', 'p', 't' }, { ' ', 'O', 'c', 148 | 't', ' ' }, { ' ', 'N', 'o', 'v', ' ' }, { ' ', 'D', 'e', 'c', ' ' } }; 149 | //days 150 | char WT_arr[7][4] = { { 'S', 'u', 'n', ' ' }, { 'M', 'o', 'n', ' ' }, { 'T', 'u', 'e', ' ' }, { 151 | 'W', 'e', 'd', ' ' }, { 'T', 'h', 'u', ' ' }, { 'F', 'r', 'i', ' ' }, { 'S', 'a', 't', ' ' } }; 152 | 153 | // Zeichensatz 5x8 in einer 8x8 Matrix, 0,0 ist rechts oben 154 | unsigned short const font1[96][9] = { 155 | { 0x07, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00 }, // 0x20, Space 156 | { 0x07, 0x04, 0x04, 0x04, 0x04, 0x04, 0x00, 0x04, 0x00 }, // 0x21, ! 157 | { 0x07, 0x09, 0x09, 0x12, 0x00, 0x00, 0x00, 0x00, 0x00 }, // 0x22, " 158 | { 0x07, 0x0a, 0x0a, 0x1f, 0x0a, 0x1f, 0x0a, 0x0a, 0x00 }, // 0x23, # 159 | // { 0x07, 0x04, 0x0f, 0x14, 0x0e, 0x05, 0x1e, 0x04, 0x00 }, // 0x24, $ 160 | { 0x07, 0x06, 0x09, 0x09, 0x06, 0x00, 0x00, 0x00, 0x00 }, // 0x24, $ changed with degree sign 161 | { 0x07, 0x19, 0x19, 0x02, 0x04, 0x08, 0x13, 0x13, 0x00 }, // 0x25, % 162 | { 0x07, 0x04, 0x0a, 0x0a, 0x0a, 0x15, 0x12, 0x0d, 0x00 }, // 0x26, & 163 | { 0x07, 0x04, 0x04, 0x08, 0x00, 0x00, 0x00, 0x00, 0x00 }, // 0x27, ' 164 | { 0x07, 0x02, 0x04, 0x08, 0x08, 0x08, 0x04, 0x02, 0x00 }, // 0x28, ( 165 | { 0x07, 0x08, 0x04, 0x02, 0x02, 0x02, 0x04, 0x08, 0x00 }, // 0x29, ) 166 | { 0x07, 0x04, 0x15, 0x0e, 0x1f, 0x0e, 0x15, 0x04, 0x00 }, // 0x2a, * 167 | { 0x07, 0x00, 0x04, 0x04, 0x1f, 0x04, 0x04, 0x00, 0x00 }, // 0x2b, + 168 | { 0x04, 0x00, 0x00, 0x00, 0x00, 0x00, 0x01, 0x01, 0x02 }, // 0x2c, , 169 | { 0x07, 0x00, 0x00, 0x00, 0x1f, 0x00, 0x00, 0x00, 0x00 }, // 0x2d, - 170 | { 0x04, 0x00, 0x00, 0x00, 0x00, 0x00, 0x03, 0x03, 0x00 }, // 0x2e, . 171 | { 0x07, 0x01, 0x01, 0x02, 0x04, 0x08, 0x10, 0x10, 0x00 }, // 0x2f, / 172 | { 0x07, 0x0e, 0x11, 0x13, 0x15, 0x19, 0x11, 0x0e, 0x00 }, // 0x30, 0 173 | { 0x07, 0x04, 0x0c, 0x04, 0x04, 0x04, 0x04, 0x0e, 0x00 }, // 0x31, 1 174 | { 0x07, 0x0e, 0x11, 0x01, 0x02, 0x04, 0x08, 0x1f, 0x00 }, // 0x32, 2 175 | { 0x07, 0x0e, 0x11, 0x01, 0x06, 0x01, 0x11, 0x0e, 0x00 }, // 0x33, 3 176 | { 0x07, 0x02, 0x06, 0x0a, 0x12, 0x1f, 0x02, 0x02, 0x00 }, // 0x34, 4 177 | { 0x07, 0x1f, 0x10, 0x1e, 0x01, 0x01, 0x11, 0x0e, 0x00 }, // 0x35, 5 178 | { 0x07, 0x06, 0x08, 0x10, 0x1e, 0x11, 0x11, 0x0e, 0x00 }, // 0x36, 6 179 | { 0x07, 0x1f, 0x01, 0x02, 0x04, 0x08, 0x08, 0x08, 0x00 }, // 0x37, 7 180 | { 0x07, 0x0e, 0x11, 0x11, 0x0e, 0x11, 0x11, 0x0e, 0x00 }, // 0x38, 8 181 | { 0x07, 0x0e, 0x11, 0x11, 0x0f, 0x01, 0x02, 0x0c, 0x00 }, // 0x39, 9 182 | { 0x04, 0x00, 0x03, 0x03, 0x00, 0x03, 0x03, 0x00, 0x00 }, // 0x3a, : 183 | { 0x07, 0x00, 0x0c, 0x0c, 0x00, 0x0c, 0x04, 0x08, 0x00 }, // 0x3b, ; 184 | { 0x07, 0x02, 0x04, 0x08, 0x10, 0x08, 0x04, 0x02, 0x00 }, // 0x3c, < 185 | { 0x07, 0x00, 0x00, 0x1f, 0x00, 0x1f, 0x00, 0x00, 0x00 }, // 0x3d, = 186 | { 0x07, 0x08, 0x04, 0x02, 0x01, 0x02, 0x04, 0x08, 0x00 }, // 0x3e, > 187 | { 0x07, 0x0e, 0x11, 0x01, 0x02, 0x04, 0x00, 0x04, 0x00 }, // 0x3f, ? 188 | { 0x07, 0x0e, 0x11, 0x17, 0x15, 0x17, 0x10, 0x0f, 0x00 }, // 0x40, @ 189 | { 0x07, 0x04, 0x0a, 0x11, 0x11, 0x1f, 0x11, 0x11, 0x00 }, // 0x41, A 190 | { 0x07, 0x1e, 0x11, 0x11, 0x1e, 0x11, 0x11, 0x1e, 0x00 }, // 0x42, B 191 | { 0x07, 0x0e, 0x11, 0x10, 0x10, 0x10, 0x11, 0x0e, 0x00 }, // 0x43, C 192 | { 0x07, 0x1e, 0x09, 0x09, 0x09, 0x09, 0x09, 0x1e, 0x00 }, // 0x44, D 193 | { 0x07, 0x1f, 0x10, 0x10, 0x1c, 0x10, 0x10, 0x1f, 0x00 }, // 0x45, E 194 | { 0x07, 0x1f, 0x10, 0x10, 0x1f, 0x10, 0x10, 0x10, 0x00 }, // 0x46, F 195 | { 0x07, 0x0e, 0x11, 0x10, 0x10, 0x13, 0x11, 0x0f, 0x00 }, // 0x37, G 196 | { 0x07, 0x11, 0x11, 0x11, 0x1f, 0x11, 0x11, 0x11, 0x00 }, // 0x48, H 197 | { 0x07, 0x0e, 0x04, 0x04, 0x04, 0x04, 0x04, 0x0e, 0x00 }, // 0x49, I 198 | { 0x07, 0x1f, 0x02, 0x02, 0x02, 0x02, 0x12, 0x0c, 0x00 }, // 0x4a, J 199 | { 0x07, 0x11, 0x12, 0x14, 0x18, 0x14, 0x12, 0x11, 0x00 }, // 0x4b, K 200 | { 0x07, 0x10, 0x10, 0x10, 0x10, 0x10, 0x10, 0x1f, 0x00 }, // 0x4c, L 201 | { 0x07, 0x11, 0x1b, 0x15, 0x11, 0x11, 0x11, 0x11, 0x00 }, // 0x4d, M 202 | { 0x07, 0x11, 0x11, 0x19, 0x15, 0x13, 0x11, 0x11, 0x00 }, // 0x4e, N 203 | { 0x07, 0x0e, 0x11, 0x11, 0x11, 0x11, 0x11, 0x0e, 0x00 }, // 0x4f, O 204 | { 0x07, 0x1e, 0x11, 0x11, 0x1e, 0x10, 0x10, 0x10, 0x00 }, // 0x50, P 205 | { 0x07, 0x0e, 0x11, 0x11, 0x11, 0x15, 0x12, 0x0d, 0x00 }, // 0x51, Q 206 | { 0x07, 0x1e, 0x11, 0x11, 0x1e, 0x14, 0x12, 0x11, 0x00 }, // 0x52, R 207 | { 0x07, 0x0e, 0x11, 0x10, 0x0e, 0x01, 0x11, 0x0e, 0x00 }, // 0x53, S 208 | { 0x07, 0x1f, 0x04, 0x04, 0x04, 0x04, 0x04, 0x04, 0x00 }, // 0x54, T 209 | { 0x07, 0x11, 0x11, 0x11, 0x11, 0x11, 0x11, 0x0e, 0x00 }, // 0x55, U 210 | { 0x07, 0x11, 0x11, 0x11, 0x11, 0x11, 0x0a, 0x04, 0x00 }, // 0x56, V 211 | { 0x07, 0x11, 0x11, 0x11, 0x15, 0x15, 0x1b, 0x11, 0x00 }, // 0x57, W 212 | { 0x07, 0x11, 0x11, 0x0a, 0x04, 0x0a, 0x11, 0x11, 0x00 }, // 0x58, X 213 | { 0x07, 0x11, 0x11, 0x0a, 0x04, 0x04, 0x04, 0x04, 0x00 }, // 0x59, Y 214 | { 0x07, 0x1f, 0x01, 0x02, 0x04, 0x08, 0x10, 0x1f, 0x00 }, // 0x5a, Z 215 | { 0x07, 0x0e, 0x08, 0x08, 0x08, 0x08, 0x08, 0x0e, 0x00 }, // 0x5b, [ 216 | { 0x07, 0x10, 0x10, 0x08, 0x04, 0x02, 0x01, 0x01, 0x00 }, // 0x5c, '\' 217 | { 0x07, 0x0e, 0x02, 0x02, 0x02, 0x02, 0x02, 0x0e, 0x00 }, // 0x5d, ] 218 | { 0x07, 0x04, 0x0a, 0x11, 0x00, 0x00, 0x00, 0x00, 0x00 }, // 0x5e, ^ 219 | { 0x07, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x1f, 0x00 }, // 0x5f, _ 220 | { 0x07, 0x04, 0x04, 0x02, 0x00, 0x00, 0x00, 0x00, 0x00 }, // 0x60, ` 221 | { 0x07, 0x00, 0x0e, 0x01, 0x0d, 0x13, 0x13, 0x0d, 0x00 }, // 0x61, a 222 | { 0x07, 0x10, 0x10, 0x10, 0x1c, 0x12, 0x12, 0x1c, 0x00 }, // 0x62, b 223 | { 0x07, 0x00, 0x00, 0x00, 0x0e, 0x10, 0x10, 0x0e, 0x00 }, // 0x63, c 224 | { 0x07, 0x01, 0x01, 0x01, 0x07, 0x09, 0x09, 0x07, 0x00 }, // 0x64, d 225 | { 0x07, 0x00, 0x00, 0x0e, 0x11, 0x1f, 0x10, 0x0f, 0x00 }, // 0x65, e 226 | { 0x07, 0x06, 0x09, 0x08, 0x1c, 0x08, 0x08, 0x08, 0x00 }, // 0x66, f 227 | { 0x07, 0x00, 0x0e, 0x11, 0x13, 0x0d, 0x01, 0x01, 0x0e }, // 0x67, g 228 | { 0x07, 0x10, 0x10, 0x10, 0x16, 0x19, 0x11, 0x11, 0x00 }, // 0x68, h 229 | { 0x05, 0x00, 0x02, 0x00, 0x06, 0x02, 0x02, 0x07, 0x00 }, // 0x69, i 230 | { 0x07, 0x00, 0x02, 0x00, 0x06, 0x02, 0x02, 0x12, 0x0c }, // 0x6a, j 231 | { 0x07, 0x10, 0x10, 0x12, 0x14, 0x18, 0x14, 0x12, 0x00 }, // 0x6b, k 232 | { 0x05, 0x06, 0x02, 0x02, 0x02, 0x02, 0x02, 0x02, 0x00 }, // 0x6c, l 233 | { 0x07, 0x00, 0x00, 0x0a, 0x15, 0x15, 0x11, 0x11, 0x00 }, // 0x6d, m 234 | { 0x07, 0x00, 0x00, 0x16, 0x19, 0x11, 0x11, 0x11, 0x00 }, // 0x6e, n 235 | { 0x07, 0x00, 0x00, 0x0e, 0x11, 0x11, 0x11, 0x0e, 0x00 }, // 0x6f, o 236 | { 0x07, 0x00, 0x00, 0x1c, 0x12, 0x12, 0x1c, 0x10, 0x10 }, // 0x70, p 237 | { 0x07, 0x00, 0x00, 0x07, 0x09, 0x09, 0x07, 0x01, 0x01 }, // 0x71, q 238 | { 0x07, 0x00, 0x00, 0x16, 0x19, 0x10, 0x10, 0x10, 0x00 }, // 0x72, r 239 | { 0x07, 0x00, 0x00, 0x0f, 0x10, 0x0e, 0x01, 0x1e, 0x00 }, // 0x73, s 240 | { 0x07, 0x08, 0x08, 0x1c, 0x08, 0x08, 0x09, 0x06, 0x00 }, // 0x74, t 241 | { 0x07, 0x00, 0x00, 0x11, 0x11, 0x11, 0x13, 0x0d, 0x00 }, // 0x75, u 242 | { 0x07, 0x00, 0x00, 0x11, 0x11, 0x11, 0x0a, 0x04, 0x00 }, // 0x76, v 243 | { 0x07, 0x00, 0x00, 0x11, 0x11, 0x15, 0x15, 0x0a, 0x00 }, // 0x77, w 244 | { 0x07, 0x00, 0x00, 0x11, 0x0a, 0x04, 0x0a, 0x11, 0x00 }, // 0x78, x 245 | { 0x07, 0x00, 0x00, 0x11, 0x11, 0x0f, 0x01, 0x11, 0x0e }, // 0x79, y 246 | { 0x07, 0x00, 0x00, 0x1f, 0x02, 0x04, 0x08, 0x1f, 0x00 }, // 0x7a, z 247 | { 0x07, 0x06, 0x08, 0x08, 0x10, 0x08, 0x08, 0x06, 0x00 }, // 0x7b, { 248 | { 0x07, 0x04, 0x04, 0x04, 0x00, 0x04, 0x04, 0x04, 0x00 }, // 0x7c, | 249 | { 0x07, 0x0c, 0x02, 0x02, 0x01, 0x02, 0x02, 0x0c, 0x00 }, // 0x7d, } 250 | { 0x07, 0x08, 0x15, 0x02, 0x00, 0x00, 0x00, 0x00, 0x00 }, // 0x7e, ~ 251 | { 0x07, 0x1f, 0x1f, 0x1f, 0x1f, 0x1f, 0x1f, 0x1f, 0x00 } // 0x7f, DEL 252 | }; 253 | //************************************************************************************************** 254 | void connect_to_WiFi() { // We start by connecting to a WiFi network 255 | Serial.println(""); 256 | Serial.print("Connecting to "); 257 | Serial.println(ssid); 258 | 259 | WiFi.mode(WIFI_STA); 260 | WiFi.begin(ssid, pass); 261 | 262 | while (WiFi.status() != WL_CONNECTED) { 263 | delay(500); 264 | Serial.print("."); 265 | } 266 | Serial.println(""); 267 | 268 | Serial.println("WiFi connected"); 269 | Serial.print("IP address: "); 270 | Serial.println(String(WiFi.localIP())); 271 | Serial.println("Starting UDP"); 272 | udp.begin(localPort); 273 | Serial.print("Local port: "); 274 | Serial.println(udp.localPort()); 275 | } 276 | //************************************************************************************************** 277 | tm* connectNTP() { //if response from NTP was succesfull return *tm else return a nullpointer 278 | WiFi.hostByName(ntpServerName, timeServerIP); 279 | Serial.println(timeServerIP); 280 | Serial.println("sending NTP packet..."); 281 | // set all bytes in the buffer to 0 282 | memset(packetBuffer, 0, NTP_PACKET_SIZE); 283 | // Initialize values needed to form NTP request 284 | // (see URL above for details on the packets) 285 | packetBuffer[0] = 0b11100011; // LI, Version, Mode 286 | packetBuffer[1] = 0; // Stratum, or type of clock 287 | packetBuffer[2] = 6; // Polling Interval 288 | packetBuffer[3] = 0xEC; // Peer Clock Precision 289 | // 8 bytes of zero for Root Delay & Root Dispersion 290 | packetBuffer[12] = 49; 291 | packetBuffer[13] = 0x4E; 292 | packetBuffer[14] = 49; 293 | packetBuffer[15] = 52; 294 | // all NTP fields have been given values, now 295 | // you can send a packet requesting a timestamp: 296 | udp.beginPacket(timeServerIP, 123); //NTP requests are to port 123 297 | udp.write(packetBuffer, NTP_PACKET_SIZE); 298 | udp.endPacket(); 299 | delay(1000); // wait to see if a reply is available 300 | int cb = udp.parsePacket(); 301 | udp.read(packetBuffer, NTP_PACKET_SIZE); // read the packet into the buffer 302 | //the timestamp starts at byte 40 of the received packet and is four bytes, 303 | // or two words, long. First, esxtract the two words: 304 | unsigned long highWord = word(packetBuffer[40], packetBuffer[41]); 305 | unsigned long lowWord = word(packetBuffer[42], packetBuffer[43]); 306 | // combine the four bytes (two words) into a long integer 307 | // this is NTP time (seconds since Jan 1 1900): 308 | unsigned long secsSince1900 = highWord << 16 | lowWord; 309 | // now convert NTP time into everyday time: 310 | const unsigned long seventyYears = 2208988800UL; 311 | // subtract seventy years: 312 | epoch = secsSince1900 - seventyYears +2; //+2000ms Verarbeitungszeit 313 | epoch=epoch+3600*corectie; // difference -6h = -6* 3600 sec) 314 | time_t t; 315 | t = epoch; 316 | tm* tt; 317 | tt = localtime(&t); 318 | if (cb == 48) 319 | return (tt); 320 | else 321 | return (NULL); 322 | } 323 | //************************************************************************************************** 324 | void rtc_init(unsigned char sda, unsigned char scl) { 325 | Wire.begin(sda, scl); 326 | rtc_Write(controlREG, 0x00); 327 | } 328 | //************************************************************************************************** 329 | // BCD Code 330 | //************************************************************************************************** 331 | unsigned char dec2bcd(unsigned char x) { //value 0...99 332 | unsigned char z, e, r; 333 | e = x % 10; 334 | z = x / 10; 335 | z = z << 4; 336 | r = e | z; 337 | return (r); 338 | } 339 | unsigned char bcd2dec(unsigned char x) { //value 0...99 340 | int z, e; 341 | e = x & 0x0F; 342 | z = x & 0xF0; 343 | z = z >> 4; 344 | z = z * 10; 345 | return (z + e); 346 | } 347 | //************************************************************************************************** 348 | // RTC I2C Code 349 | //************************************************************************************************** 350 | unsigned char rtc_Read(unsigned char regaddress) { 351 | Wire.beginTransmission(DS3231_ADDRESS); 352 | Wire.write(regaddress); 353 | Wire.endTransmission(); 354 | Wire.requestFrom((unsigned char) DS3231_ADDRESS, (unsigned char) 1); 355 | return (Wire.read()); 356 | } 357 | void rtc_Write(unsigned char regaddress, unsigned char value) { 358 | Wire.beginTransmission(DS3231_ADDRESS); 359 | Wire.write(regaddress); 360 | Wire.write(value); 361 | Wire.endTransmission(); 362 | } 363 | //************************************************************************************************** 364 | unsigned char rtc_sekunde() { 365 | return (bcd2dec(rtc_Read(secondREG))); 366 | } 367 | unsigned char rtc_minute() { 368 | return (bcd2dec(rtc_Read(minuteREG))); 369 | } 370 | unsigned char rtc_stunde() { 371 | return (bcd2dec(rtc_Read(hourREG))); 372 | } 373 | unsigned char rtc_wochentag() { 374 | return (bcd2dec(rtc_Read(WTREG))); 375 | } 376 | unsigned char rtc_tag() { 377 | return (bcd2dec(rtc_Read(dateREG))); 378 | } 379 | unsigned char rtc_monat() { 380 | return (bcd2dec(rtc_Read(monthREG))); 381 | } 382 | unsigned char rtc_jahr() { 383 | return (bcd2dec(rtc_Read(yearREG))); 384 | } 385 | void rtc_sekunde(unsigned char sek) { 386 | rtc_Write(secondREG, (dec2bcd(sek))); 387 | } 388 | void rtc_minute(unsigned char min) { 389 | rtc_Write(minuteREG, (dec2bcd(min))); 390 | } 391 | void rtc_stunde(unsigned char std) { 392 | rtc_Write(hourREG, (dec2bcd(std))); 393 | } 394 | void rtc_wochentag(unsigned char wt) { 395 | rtc_Write(WTREG, (dec2bcd(wt))); 396 | } 397 | void rtc_tag(unsigned char tag) { 398 | rtc_Write(dateREG, (dec2bcd(tag))); 399 | } 400 | void rtc_monat(unsigned char mon) { 401 | rtc_Write(monthREG, (dec2bcd(mon))); 402 | } 403 | void rtc_jahr(unsigned char jahr) { 404 | rtc_Write(yearREG, (dec2bcd(jahr))); 405 | } 406 | //************************************************************************************************** 407 | void rtc_set(tm* tt) { 408 | rtc_sekunde((unsigned char) tt->tm_sec); 409 | rtc_minute((unsigned char) tt->tm_min); 410 | rtc_stunde((unsigned char) tt->tm_hour); 411 | rtc_tag((unsigned char) tt->tm_mday); 412 | rtc_monat((unsigned char) tt->tm_mon + 1); 413 | rtc_jahr((unsigned char) tt->tm_year - 100); 414 | rtc_wochentag((unsigned char) tt->tm_wday); 415 | } 416 | //************************************************************************************************** 417 | float rtc_temp() { 418 | float t = 0.0; 419 | unsigned char lowByte = 0; 420 | signed char highByte = 0; 421 | lowByte = rtc_Read(tempLSBREG); 422 | highByte = rtc_Read(tempMSBREG); 423 | lowByte >>= 6; 424 | lowByte &= 0x03; 425 | t = ((float) lowByte); 426 | t *= 0.25; 427 | t += highByte; 428 | return (t); // return temp value 429 | } 430 | //************************************************************************************************** 431 | void rtc2mez() { 432 | 433 | unsigned short JaZiff; //Jahresziffer 434 | unsigned short JhZiff = 6; //Jahrhundertziffer für 20.Jahrhundert 435 | unsigned short TaZiff; //Tagesziffer 436 | unsigned short WoTag; //Wochentag 437 | unsigned short SJK = 0; //Schaltjahreskorrektur 438 | unsigned short ZDiff; //Zeitdifferenz UTC MEZ/MESZ 439 | unsigned short MoZiff[12] = { 0, 3, 3, 6, 1, 4, 6, 2, 5, 0, 3, 5 }; //Monatsziffer 440 | unsigned short Tage_Monat[12] = { 31, 28, 31, 30, 31, 30, 31, 31, 30, 31, 30, 441 | 31 }; 442 | unsigned short Jahr, Tag, Monat, Stunde, Minute, Sekunde; 443 | //RTC_setMonat(3); 444 | Jahr = rtc_jahr(); 445 | if (Jahr > 99) 446 | Jahr = 0; 447 | Monat = rtc_monat(); 448 | if (Monat > 12) 449 | Monat = 0; 450 | Tag = rtc_tag(); 451 | if (Tag > 31) 452 | Tag = 0; 453 | Stunde = rtc_stunde(); 454 | if (Stunde > 23) 455 | Stunde = 0; 456 | Minute = rtc_minute(); 457 | if (Minute > 59) 458 | Minute = 0; 459 | Sekunde = rtc_sekunde(); 460 | if (Sekunde > 59) 461 | Sekunde = 0; 462 | 463 | JaZiff = ((Jahr + Jahr / 4) % 7); 464 | TaZiff = (Tag % 7); 465 | if ((Jahr % 4) == 0) //Schaltjahr ? 466 | { 467 | Tage_Monat[1] = 29; //dann hat der Febr 29 Tage 468 | if (Monat < 3) 469 | SJK = 6; 470 | else 471 | SJK = 0; 472 | } 473 | WoTag = ((TaZiff + MoZiff[Monat - 1] + JhZiff + JaZiff + SJK) % 7); 474 | 475 | if (Monat < 3 || Monat > 10) 476 | ZDiff = 1; // keine Sommerzeit in Jan, Feb, Nov, Dez 477 | if (Monat > 3 && Monat < 10) 478 | ZDiff = 2; // Sommerz. in Apr, Mai, Jun, Jul, Aug, Sep 479 | if (Monat == 3) { 480 | ZDiff = 1; 481 | if (Tag > 24) //Sommerzeit ab letzten Sonntag des Monats 482 | { 483 | if (Tag == 25) { 484 | if ((Tag + WoTag) < 26) 485 | ZDiff = 2; 486 | } 487 | if (Tag == 26) { 488 | if ((Tag + WoTag) < 28) 489 | ZDiff = 2; 490 | } 491 | if (Tag == 27) { 492 | if ((Tag + WoTag) < 30) 493 | ZDiff = 2; 494 | } 495 | if (Tag == 28) { 496 | if ((Tag + WoTag) < 32) 497 | ZDiff = 2; 498 | } 499 | if (Tag == 29) { 500 | if ((Tag + WoTag) < 34) 501 | ZDiff = 2; 502 | } 503 | if (Tag == 30) { 504 | if ((Tag + WoTag) < 36) 505 | ZDiff = 2; 506 | } 507 | if (Tag == 31) { 508 | if ((Tag + WoTag) < 38) 509 | ZDiff = 2; 510 | } 511 | if ((ZDiff == 2) && (Stunde + 1 < 2) && (WoTag == 0)) 512 | ZDiff = 1; //erst ab 02 Uhr 513 | } 514 | } 515 | if (Monat == 10) { 516 | ZDiff = 2; 517 | if (Tag > 24) //Sommerzeit ab letzten Sonntag des Monats 518 | { 519 | if (Tag == 25) { 520 | if ((Tag + WoTag) < 26) 521 | ZDiff = 1; 522 | } 523 | if (Tag == 26) { 524 | if ((Tag + WoTag) < 28) 525 | ZDiff = 1; 526 | } 527 | if (Tag == 27) { 528 | if ((Tag + WoTag) < 30) 529 | ZDiff = 1; 530 | } 531 | if (Tag == 28) { 532 | if ((Tag + WoTag) < 32) 533 | ZDiff = 1; 534 | } 535 | if (Tag == 29) { 536 | if ((Tag + WoTag) < 34) 537 | ZDiff = 1; 538 | } 539 | if (Tag == 30) { 540 | if ((Tag + WoTag) < 36) 541 | ZDiff = 1; 542 | } 543 | if (Tag == 31) { 544 | if ((Tag + WoTag) < 38) 545 | ZDiff = 1; 546 | } 547 | if ((ZDiff == 1) && (Stunde == 0) && (WoTag == 0)) 548 | ZDiff = 2; //erst ab 02 Uhr 549 | } 550 | } 551 | Stunde = Stunde + ZDiff; 552 | if (Stunde > 23) //Tageskorrektur 553 | { 554 | Stunde = Stunde - 24; //kann 0 oder 1 sein 555 | Tag = Tag + 1; 556 | WoTag = WoTag + 1; 557 | if (Tag > Tage_Monat[Monat - 1]) { 558 | Tag = 1; 559 | Monat = Monat + 1; 560 | if (Monat > 12) { 561 | Monat = 1; 562 | Jahr = Jahr + 1; 563 | } 564 | } 565 | } 566 | MEZ.WT = WoTag; //So=0, Mo=1, Di=2 ... 567 | MEZ.sek1 = Sekunde % 10; 568 | MEZ.sek2 = Sekunde / 10; 569 | MEZ.sek12 = Sekunde; 570 | MEZ.min1 = Minute % 10; 571 | MEZ.min2 = Minute / 10; 572 | MEZ.min12 = Minute; 573 | MEZ.std1 = Stunde % 10; 574 | MEZ.std2 = Stunde / 10; 575 | MEZ.std12 = Stunde; 576 | MEZ.tag12 = Tag; 577 | MEZ.tag1 = Tag % 10; 578 | MEZ.tag2 = Tag / 10; 579 | MEZ.mon12 = Monat; 580 | MEZ.mon1 = Monat % 10; 581 | MEZ.mon2 = Monat / 10; 582 | MEZ.jahr12 = Jahr; 583 | MEZ.jahr1 = Jahr % 10; 584 | MEZ.jahr2 = Jahr / 10; 585 | } 586 | 587 | //************************************************************************************************* 588 | const unsigned short InitArr[7][2] = { { 0x0C, 0x00 }, // display off 589 | { 0x00, 0xFF }, // no LEDtest 590 | { 0x09, 0x00 }, // BCD off 591 | { 0x0F, 0x00 }, // normal operation 592 | { 0x0B, 0x07 }, // start display 593 | { 0x0A, 0x04 }, // brightness 594 | { 0x0C, 0x01 } // display on 595 | }; 596 | //************************************************************************************************** 597 | void max7219_init() //all MAX7219 init 598 | { 599 | unsigned short i, j; 600 | for (i = 0; i < 7; i++) { 601 | digitalWrite(CS, LOW); 602 | delayMicroseconds(1); 603 | for (j = 0; j < anzMAX; j++) { 604 | SPI.write(InitArr[i][0]); //register 605 | SPI.write(InitArr[i][1]); //value 606 | } 607 | digitalWrite(CS, HIGH); 608 | } 609 | } 610 | //************************************************************************************************** 611 | void max7219_set_brightness(unsigned short br) //brightness MAX7219 612 | { 613 | unsigned short j; 614 | if (br < 16) { 615 | digitalWrite(CS, LOW); 616 | delayMicroseconds(1); 617 | for (j = 0; j < anzMAX; j++) { 618 | SPI.write(0x0A); //register 619 | SPI.write(br); //value 620 | } 621 | digitalWrite(CS, HIGH); 622 | } 623 | } 624 | //************************************************************************************************** 625 | void helpArr_init(void) //helperarray init 626 | { 627 | unsigned short i, j, k; 628 | j = 0; 629 | k = 0; 630 | for (i = 0; i < anzMAX * 8; i++) { 631 | helpArrPos[i] = (1 << j); //bitmask 632 | helpArrMAX[i] = k; 633 | j++; 634 | if (j > 7) { 635 | j = 0; 636 | k++; 637 | } 638 | } 639 | } 640 | //************************************************************************************************** 641 | void clear_Display() //clear all 642 | { 643 | unsigned short i, j; 644 | for (i = 0; i < 8; i++) //8 rows 645 | { 646 | digitalWrite(CS, LOW); 647 | delayMicroseconds(1); 648 | for (j = anzMAX; j > 0; j--) { 649 | LEDarr[j - 1][i] = 0; //LEDarr clear 650 | SPI.write(i + 1); //current row 651 | SPI.write(LEDarr[j - 1][i]); 652 | } 653 | digitalWrite(CS, HIGH); 654 | } 655 | } 656 | //********************************************************************************************************* 657 | void rotate_90() // for Generic displays 658 | { 659 | for (uint8_t k = anzMAX; k > 0; k--) { 660 | 661 | uint8_t i, j, m, imask, jmask; 662 | uint8_t tmp[8]={0,0,0,0,0,0,0,0}; 663 | for ( i = 0, imask = 0x01; i < 8; i++, imask <<= 1) { 664 | for (j = 0, jmask = 0x01; j < 8; j++, jmask <<= 1) { 665 | if (LEDarr[k-1][i] & jmask) { 666 | tmp[j] |= imask; 667 | } 668 | } 669 | } 670 | for(m=0; m<8; m++){ 671 | LEDarr[k-1][m]=tmp[m]; 672 | } 673 | } 674 | } 675 | //************************************************************************************************** 676 | void refresh_display() //take info into LEDarr 677 | { 678 | unsigned short i, j; 679 | 680 | #ifdef ROTATE_90 681 | rotate_90(); 682 | #endif 683 | 684 | for (i = 0; i < 8; i++) //8 rows 685 | { 686 | digitalWrite(CS, LOW); 687 | delayMicroseconds(1); 688 | for (j = anzMAX; j > 0; j--) { 689 | SPI.write(i + 1); //current row 690 | 691 | #ifdef REVERSE_HORIZONTAL 692 | SPI.setBitOrder(LSBFIRST); // bitorder for reverse columns 693 | #endif 694 | 695 | #ifdef REVERSE_VERTICAL 696 | SPI.write(LEDarr[j - 1][7-i]); 697 | #else 698 | SPI.write(LEDarr[j - 1][i]); 699 | #endif 700 | 701 | #ifdef REVERSE_HORIZONTAL 702 | SPI.setBitOrder(MSBFIRST); // reset bitorder 703 | #endif 704 | } 705 | digitalWrite(CS, HIGH); 706 | } 707 | } 708 | //************************************************************************************************** 709 | void char2Arr(unsigned short ch, int PosX, short PosY) { //characters into arr 710 | int i, j, k, l, m, o1, o2, o3, o4; //in LEDarr 711 | PosX++; 712 | k = ch - 32; //ASCII position in font 713 | if ((k >= 0) && (k < 96)) //character found in font? 714 | { 715 | o4 = font1[k][0]; //character width 716 | o3 = 1 << (o4 - 2); 717 | for (i = 0; i < o4; i++) { 718 | if (((PosX - i <= maxPosX) && (PosX - i >= 0)) 719 | && ((PosY > -8) && (PosY < 8))) //within matrix? 720 | { 721 | o1 = helpArrPos[PosX - i]; 722 | o2 = helpArrMAX[PosX - i]; 723 | for (j = 0; j < 8; j++) { 724 | if (((PosY >= 0) && (PosY <= j)) || ((PosY < 0) && (j < PosY + 8))) //scroll vertical 725 | { 726 | l = font1[k][j + 1]; 727 | m = (l & (o3 >> i)); //e.g. o4=7 0zzzzz0, o4=4 0zz0 728 | if (m > 0) 729 | LEDarr[o2][j - PosY] = LEDarr[o2][j - PosY] | (o1); //set point 730 | else 731 | LEDarr[o2][j - PosY] = LEDarr[o2][j - PosY] & (~o1); //clear point 732 | } 733 | } 734 | } 735 | } 736 | } 737 | } 738 | 739 | //************************************************************************************************** 740 | void timer50ms() { 741 | static unsigned int cnt50ms = 0; 742 | static unsigned int cnt1s = 0; 743 | static unsigned int cnt1h = 0; 744 | f_tckr50ms = true; 745 | cnt50ms++; 746 | if (cnt50ms == 20) { 747 | f_tckr1s = true; // 1 sec 748 | cnt1s++; 749 | cnt50ms = 0; 750 | } 751 | if (cnt1s == 3600) { // 1h 752 | cnt1h++; 753 | cnt1s = 0; 754 | } 755 | if (cnt1h == 24) { // 1d 756 | f_tckr24h = true; 757 | cnt1h = 0; 758 | } 759 | } 760 | //************************************************************************************************** 761 | // 762 | //The setup function is called once at startup of the sketch 763 | void setup() { 764 | // Add your initialization code here 765 | pinMode(CS, OUTPUT); 766 | digitalWrite(CS, HIGH); 767 | Serial.begin(115200); 768 | dht.begin(); 769 | temperatura = dht.readTemperature(); 770 | umiditate = dht.readHumidity(); 771 | Serial.print(temperatura); 772 | Serial.println("gr.Celsius"); 773 | //rtc.init(SDA, SCL); 774 | SPI.begin(); 775 | helpArr_init(); 776 | max7219_init(); 777 | max7219_set_brightness(1); 778 | rtc_init(SDA, SCL); 779 | clear_Display(); 780 | tckr.attach(0.05, timer50ms); // every 50 msec 781 | connect_to_WiFi(); 782 | tm* tt; 783 | tt = connectNTP(); 784 | if (tt != NULL) 785 | rtc_set(tt); 786 | else 787 | Serial.println("no timepacket received"); 788 | } 789 | //************************************************************************************************** 790 | // The loop function is called in an endless loop 791 | void loop() { 792 | //Add your repeated code here 793 | unsigned int sek1 = 0, sek2 = 0, min1 = 0, min2 = 0, std1 = 0, std2 = 0; 794 | unsigned int sek11 = 0, sek12 = 0, sek21 = 0, sek22 = 0; 795 | unsigned int min11 = 0, min12 = 0, min21 = 0, min22 = 0; 796 | unsigned int std11 = 0, std12 = 0, std21 = 0, std22 = 0; 797 | signed int x = 0; //x1,x2; 798 | signed int y = 0, y1 = 0, y2 = 0; 799 | bool updown = false; 800 | unsigned int sc1 = 0, sc2 = 0, sc3 = 0, sc4 = 0, sc5 = 0, sc6 = 0; 801 | bool f_scrollend_y = false; 802 | unsigned int f_scroll_x = false; 803 | 804 | // temperatura = random(-20,25); 805 | // umiditate = random(1,55); 806 | 807 | 808 | z_PosX = maxPosX; 809 | d_PosX = -8; 810 | // x=0; x1=0; x2=0; 811 | 812 | refresh_display(); 813 | updown = true; 814 | if (updown == false) { 815 | y2 = -9; 816 | y1 = 8; 817 | } 818 | if (updown == true) { //scroll up to down 819 | y2 = 8; 820 | y1 = -8; 821 | } 822 | while (true) { 823 | yield(); 824 | if (f_tckr24h == true) { //syncronisize RTC every day 825 | f_tckr24h = false; 826 | tm* tt; 827 | tt = connectNTP(); 828 | if (tt != NULL) 829 | rtc_set(tt); 830 | else 831 | Serial.println("no timepacket received"); 832 | } 833 | if (f_tckr1s == true) // flag 1sek 834 | { 835 | rtc2mez(); 836 | sek1 = MEZ.sek1; 837 | sek2 = MEZ.sek2; 838 | min1 = MEZ.min1; 839 | min2 = MEZ.min2; 840 | std1 = MEZ.std1; 841 | std2 = MEZ.std2; 842 | y = y2; //scroll updown 843 | sc1 = 1; 844 | sek1++; 845 | if (sek1 == 10) { 846 | sc2 = 1; 847 | sek2++; 848 | sek1 = 0; 849 | } 850 | if (sek2 == 6) { 851 | min1++; 852 | sek2 = 0; 853 | sc3 = 1; 854 | } 855 | if (min1 == 10) { 856 | min2++; 857 | min1 = 0; 858 | sc4 = 1; 859 | } 860 | if (min2 == 6) { 861 | std1++; 862 | min2 = 0; 863 | sc5 = 1; 864 | } 865 | if (std1 == 10) { 866 | std2++; 867 | std1 = 0; 868 | sc6 = 1; 869 | } 870 | if ((std2 == 2) && (std1 == 4)) { 871 | std1 = 0; 872 | std2 = 0; 873 | sc6 = 1; 874 | } 875 | 876 | sek11 = sek12; 877 | sek12 = sek1; 878 | sek21 = sek22; 879 | sek22 = sek2; 880 | min11 = min12; 881 | min12 = min1; 882 | min21 = min22; 883 | min22 = min2; 884 | std11 = std12; 885 | std12 = std1; 886 | std21 = std22; 887 | std22 = std2; 888 | f_tckr1s = false; 889 | if (MEZ.sek12 == 45) 890 | f_scroll_x = true; 891 | if (MEZ.sek12 == 59) 892 | { 893 | temperatura = dht.readTemperature(); 894 | umiditate = dht.readHumidity(); 895 | } 896 | } // end 1s 897 | if (f_tckr50ms == true) { 898 | f_tckr50ms = false; 899 | if (f_scroll_x == true) { 900 | z_PosX++; 901 | d_PosX++; 902 | if (d_PosX == mult) 903 | z_PosX = 0; 904 | if (z_PosX == maxPosX) { 905 | f_scroll_x = false; 906 | d_PosX = -8; 907 | } 908 | } 909 | if (sc1 == 1) { 910 | if (updown == 1) 911 | y--; 912 | else 913 | y++; 914 | char2Arr(48 + sek12, z_PosX - 42, y); 915 | char2Arr(48 + sek11, z_PosX - 42, y + y1); 916 | if (y == 0) { 917 | sc1 = 0; 918 | f_scrollend_y = true; 919 | } 920 | } 921 | else 922 | char2Arr(48 + sek1, z_PosX - 42, 0); 923 | 924 | if (sc2 == 1) { 925 | char2Arr(48 + sek22, z_PosX - 36, y); 926 | char2Arr(48 + sek21, z_PosX - 36, y + y1); 927 | if (y == 0) 928 | sc2 = 0; 929 | } 930 | else 931 | char2Arr(48 + sek2, z_PosX - 36, 0); 932 | 933 | char2Arr(':', z_PosX - 32, 0); 934 | 935 | if (sc3 == 1) { 936 | char2Arr(48 + min12, z_PosX - 25, y); 937 | char2Arr(48 + min11, z_PosX - 25, y + y1); 938 | if (y == 0) 939 | sc3 = 0; 940 | } 941 | else 942 | char2Arr(48 + min1, z_PosX - 25, 0); 943 | 944 | if (sc4 == 1) { 945 | char2Arr(48 + min22, z_PosX - 19, y); 946 | char2Arr(48 + min21, z_PosX - 19, y + y1); 947 | if (y == 0) 948 | sc4 = 0; 949 | } 950 | else 951 | char2Arr(48 + min2, z_PosX - 19, 0); 952 | 953 | char2Arr(':', z_PosX - 15 + x, 0); 954 | 955 | if (sc5 == 1) { 956 | char2Arr(48 + std12, z_PosX - 8, y); 957 | char2Arr(48 + std11, z_PosX - 8, y + y1); 958 | if (y == 0) 959 | sc5 = 0; 960 | } 961 | else 962 | char2Arr(48 + std1, z_PosX - 8, 0); 963 | 964 | if (sc6 == 1) { 965 | char2Arr(48 + std22, z_PosX - 2, y); 966 | char2Arr(48 + std21, z_PosX - 2, y + y1); 967 | if (y == 0) 968 | sc6 = 0; 969 | } 970 | else 971 | char2Arr(48 + std2, z_PosX - 2, 0); 972 | 973 | char2Arr(' ', d_PosX+7, 0); 974 | char2Arr(' ', d_PosX+1, 0); 975 | char2Arr(' ', d_PosX-5, 0); 976 | poz = 11; 977 | char2Arr(WT_arr[MEZ.WT][0], d_PosX - poz, 0); //day of the week 978 | char2Arr(WT_arr[MEZ.WT][1], d_PosX - poz-6, 0); 979 | char2Arr(WT_arr[MEZ.WT][2], d_PosX - poz-12, 0); 980 | char2Arr(WT_arr[MEZ.WT][3], d_PosX - poz-18, 0); 981 | char2Arr(' ', d_PosX - poz-24, 0); 982 | char2Arr(48 + MEZ.tag2, d_PosX - poz-30, 0); //day 983 | char2Arr(48 + MEZ.tag1, d_PosX - poz-36, 0); 984 | char2Arr('-', d_PosX - poz-42, 0); 985 | 986 | char2Arr(M_arr[MEZ.mon12 - 1][1], d_PosX - poz-48, 0); 987 | char2Arr(M_arr[MEZ.mon12 - 1][2], d_PosX - poz-54, 0); 988 | char2Arr(M_arr[MEZ.mon12 - 1][3], d_PosX - poz-60, 0); 989 | 990 | char2Arr('-', d_PosX - poz-66, 0); 991 | char2Arr('2', d_PosX - poz-72, 0); //year 992 | char2Arr('0', d_PosX - poz-78, 0); 993 | char2Arr(48 + MEZ.jahr2, d_PosX - poz-84, 0); 994 | char2Arr(48 + MEZ.jahr1, d_PosX - poz-90, 0); 995 | 996 | char2Arr(' ', d_PosX - poz-96, 0); 997 | char2Arr(' ', d_PosX - poz-102, 0); 998 | char2Arr(' ', d_PosX - poz-108, 0); 999 | 1000 | poz2 = poz +108 + 6; 1001 | 1002 | // Seby part 1003 | if (temperatura >= 10) 1004 | { 1005 | char2Arr('+', d_PosX - poz2, 0); //temperature 1006 | char2Arr(48 + (temperatura / 10), d_PosX - poz2-6, 0); 1007 | char2Arr(48 + (temperatura % 10), d_PosX - poz2-12, 0); 1008 | char2Arr('$', d_PosX - poz2-18, 0); 1009 | char2Arr('C', d_PosX - poz2-24, 0); 1010 | } 1011 | if (temperatura <= 9 && temperatura >0) 1012 | { 1013 | char2Arr(' ', d_PosX - poz2, 0); //temperature 1014 | char2Arr('+', d_PosX - poz2-6, 0); 1015 | char2Arr(48 + (temperatura % 10), d_PosX - poz2-12, 0); 1016 | char2Arr('$', d_PosX - poz2-18, 0); 1017 | char2Arr('C', d_PosX - poz2-24, 0); 1018 | } 1019 | if (temperatura == 0) 1020 | { 1021 | char2Arr(' ', d_PosX - poz2, 0); //temperature 1022 | char2Arr(' ', d_PosX - poz2-6, 0); 1023 | char2Arr(48 + (temperatura % 10), d_PosX - poz2-12, 0); 1024 | char2Arr('$', d_PosX - poz2-18, 0); 1025 | char2Arr('C', d_PosX - poz2-24, 0); 1026 | } 1027 | if (temperatura < 0 && temperatura >= -9) 1028 | { 1029 | char2Arr(' ', d_PosX - poz2, 0); //temperature 1030 | char2Arr('-', d_PosX - poz2-6, 0);//the ,,abs,, turns the negative number into positive 1031 | char2Arr(48 + (abs(temperatura) % 10), d_PosX - poz2-12, 0); 1032 | char2Arr('$', d_PosX - poz2-18, 0); 1033 | char2Arr('C', d_PosX - poz2-24, 0); 1034 | } 1035 | if (temperatura < -9) 1036 | { 1037 | char2Arr('-', d_PosX - poz2, 0); //temperature 1038 | char2Arr(48 + (abs(temperatura) / 10), d_PosX - poz2-6, 0);//the ,,abs,, turns the negative number into positive 1039 | char2Arr(48 + (abs(temperatura) % 10), d_PosX - poz2-12, 0); 1040 | char2Arr('$', d_PosX - poz2-18, 0); 1041 | char2Arr('C', d_PosX - poz2-24, 0); 1042 | } 1043 | char2Arr(' ', d_PosX - poz2-30, 0); 1044 | char2Arr(' ', d_PosX - poz2-36, 0); 1045 | // char2Arr(' ', d_PosX - poz2-44, 0); 1046 | 1047 | if (umiditate >= 10) 1048 | { 1049 | char2Arr(48 + (umiditate / 10), d_PosX - poz2-42, 0); 1050 | char2Arr(48 + (umiditate % 10), d_PosX - poz2-48, 0); 1051 | char2Arr('%', d_PosX - poz2-54, 0); 1052 | char2Arr('R', d_PosX - poz2-60, 0); 1053 | char2Arr('H', d_PosX - poz2-66, 0); 1054 | } 1055 | if (temperatura <= 9 && temperatura >0) 1056 | { 1057 | char2Arr(' ', d_PosX - poz2-42, 0); 1058 | char2Arr(48 + (umiditate), d_PosX - poz2-48, 0); 1059 | char2Arr('%', d_PosX - poz2-54, 0); 1060 | char2Arr('R', d_PosX - poz2-60, 0); 1061 | char2Arr('H', d_PosX - poz2-66, 0); 1062 | } 1063 | char2Arr(' ', d_PosX - poz2-72, 0); 1064 | char2Arr(' ', d_PosX - poz2-78, 0); 1065 | char2Arr(' ', d_PosX - poz2-82, 0); 1066 | 1067 | mult = poz2 + 82 + 5; 1068 | 1069 | // end Seby part 1070 | 1071 | refresh_display(); //alle 50ms 1072 | if (f_scrollend_y == true) { 1073 | f_scrollend_y = false; 1074 | } 1075 | } //end 50ms 1076 | if (y == 0) { 1077 | // do something else 1078 | } 1079 | } //end while(true) 1080 | //this section can not be reached 1081 | } 1082 | -------------------------------------------------------------------------------- /MatrixClock_ESP8266_DHT_1.ino: -------------------------------------------------------------------------------- 1 | //********************************************************************************************************* 2 | //* ESP8266 MatrixClock by Wolle / schreibfaul1 * 3 | //********************************************************************************************************* 4 | // 5 | // first release on 26.02.2017 6 | // updated on 26.03.2019 7 | // Version 1.2.1 8 | // https://github.com/schreibfaul1/ESP8266-LED-Matrix-Clock 9 | // 10 | // THE SOFTWARE IS PROVIDED "AS IS" FOR PRIVATE USE ONLY, IT IS NOT FOR COMMERCIAL USE IN WHOLE OR PART OR CONCEPT. 11 | // FOR PERSONAL USE IT IS SUPPLIED WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE 12 | // WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHOR 13 | // OR COPYRIGHT HOLDER BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR 14 | // OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE 15 | // 16 | // 17 | // small changes by Nicu FLORICA (niq_ro), 31-May_2019 18 | // add DHT sensor for temperature and humidity 19 | // change at add text to be more easy to change 20 | 21 | #include 22 | #include 23 | #include 24 | #include 25 | #include 26 | #include 27 | #include 28 | #include "DHT.h" 29 | 30 | 31 | 32 | 33 | #define SDA 5 // Pin sda (I2C) 34 | #define SCL 4 // Pin scl (I2C) 35 | #define CS 15 // Pin cs (SPI) 36 | #define anzMAX 6 // Anzahl der kaskadierten Module 37 | 38 | char ssid[] = "SSID"; // your network SSID (name) 39 | char pass[] = "password"; // your network password 40 | 41 | // other displays ------------------------------------- 42 | #define REVERSE_HORIZONTAL // Parola, Generic and IC-Station 43 | //#define REVERSE_VERTICAL // IC-Station display 44 | #define ROTATE_90 // Generic display 45 | /* 46 | p A B C D E F G 7 6 5 4 3 2 1 0 G F E D C B A p G F E D C B A p 47 | ------------------------ ------------------------ ------------------------ ------------------------ 48 | 0 |o o o o o o o o| p |o o o o o o o o| 0 |o o o o o o o o| 7 |o o o o o o o o| 49 | 1 |o o o o o o o o| A |o o o o o o o o| 1 |o o o o o o o o| 6 |o o o o o o o o| 50 | 2 |o o o o o o o o| B |o o o o o o o o| 2 |o o o o o o o o| 5 |o o o o o o o o| 51 | 3 |o o o o| C |o o o o| 3 |o o o o| 4 |o o o o| 52 | 4 |o o FC-16 o o| D |o o Generic o o| 4 |o o Parola o o| 3 |o o IC-Station o o| 53 | 5 |o o o o| E |o o o o| 5 |o o o o| 2 |o o o o| 54 | 6 |o o o o o o o o| F |o o o o o o o o| 6 |o o o o o o o o| 1 |o o o o o o o o| 55 | 7 |o o o o o o o o| G |o o o o o o o o| 7 |o o o o o o o o| 0 |o o o o o o o o| 56 | ------------------------ ------------------------ ------------------------ ------------------------ 57 | */ 58 | 59 | // DHT sensor 60 | #define DHTPIN 12 // what pin we're connected to // GPIO 13 = D6 61 | // Uncomment whatever type you're using! 62 | //#define DHTTYPE DHT11 // DHT 11 63 | #define DHTTYPE DHT22 // DHT 22 (AM2302) 64 | //#define DHTTYPE DHT21 // DHT 21 (AM2301) 65 | // Connect pin 1 (on the left) of the sensor to +5V 66 | // NOTE: If using a board with 3.3V logic like an Arduino Due connect pin 1 67 | // to 3.3V instead of 5V! 68 | // Connect pin 2 of the sensor to whatever your DHTPIN is 69 | // Connect pin 4 (on the right) of the sensor to GROUND 70 | // Connect a 10K resistor from pin 2 (data) to pin 1 (power) of the sensor 71 | // Initialize DHT sensor for normal 16mhz Arduino 72 | //DHT dht(DHTPIN, DHTTYPE); 73 | // NOTE: For working with a faster chip, like an Arduino Due or Teensy, you 74 | // might need to increase the threshold for cycle counts considered a 1 or 0. 75 | // You can do this by passing a 3rd parameter for this threshold. It's a bit 76 | // of fiddling to find the right value, but in general the faster the CPU the 77 | // higher the value. The default for a 16mhz AVR is a value of 6. For an 78 | // Arduino Due that runs at 84mhz a value of 30 works. 79 | // Example to initialize DHT sensor for Arduino Due: 80 | DHT dht(DHTPIN, DHTTYPE, 11); // for ESP8266 81 | 82 | 83 | unsigned short maxPosX = anzMAX * 8 - 1; //calculated maxposition 84 | unsigned short LEDarr[anzMAX][8]; //character matrix to display (40*8) 85 | unsigned short helpArrMAX[anzMAX * 8]; //helperarray for chardecoding 86 | unsigned short helpArrPos[anzMAX * 8]; //helperarray pos of chardecoding 87 | unsigned int z_PosX = 0; //xPosition im Display für Zeitanzeige 88 | unsigned int d_PosX = 0; //xPosition im Display f�r Datumanzeige 89 | bool f_tckr1s = false; 90 | bool f_tckr50ms = false; 91 | bool f_tckr24h = false; 92 | unsigned long epoch = 0; 93 | unsigned int localPort = 2390; // local port to listen for UDP packets 94 | const char* ntpServerName = "time.nist.gov"; 95 | const int NTP_PACKET_SIZE = 48; // NTP time stamp is in the first 48 bytes of the message 96 | byte packetBuffer[NTP_PACKET_SIZE]; //buffer to hold incoming and outgoing packets 97 | IPAddress timeServerIP; // time.nist.gov NTP server address 98 | tm *tt, ttm; 99 | #define corectie +1 100 | 101 | int temperatura = 0; 102 | int umiditate = 0; 103 | int poz, poz2; 104 | int mult = 224; 105 | 106 | //Variablen für RTC DS3231 107 | const unsigned char DS3231_ADDRESS = 0x68; 108 | const unsigned char secondREG = 0x00; 109 | const unsigned char minuteREG = 0x01; 110 | const unsigned char hourREG = 0x02; 111 | const unsigned char WTREG = 0x03; //weekday 112 | const unsigned char dateREG = 0x04; 113 | const unsigned char monthREG = 0x05; 114 | const unsigned char yearREG = 0x06; 115 | const unsigned char alarm_min1secREG = 0x07; 116 | const unsigned char alarm_min1minREG = 0x08; 117 | const unsigned char alarm_min1hrREG = 0x09; 118 | const unsigned char alarm_min1dateREG = 0x0A; 119 | const unsigned char alarm_min2minREG = 0x0B; 120 | const unsigned char alarm_min2hrREG = 0x0C; 121 | const unsigned char alarm_min2dateREG = 0x0D; 122 | const unsigned char controlREG = 0x0E; 123 | const unsigned char statusREG = 0x0F; 124 | const unsigned char ageoffsetREG = 0x10; 125 | const unsigned char tempMSBREG = 0x11; 126 | const unsigned char tempLSBREG = 0x12; 127 | const unsigned char _24_hour_format = 0; 128 | const unsigned char _12_hour_format = 1; 129 | const unsigned char AM = 0; 130 | const unsigned char PM = 1; 131 | 132 | struct DateTime { 133 | unsigned short sek1, sek2, sek12, min1, min2, min12, std1, std2, std12; 134 | unsigned short tag1, tag2, tag12, mon1, mon2, mon12, jahr1, jahr2, jahr12, WT; 135 | } MEZ; 136 | 137 | 138 | // The object for the Ticker 139 | Ticker tckr; 140 | // A UDP instance to let us send and receive packets over UDP 141 | WiFiUDP udp; 142 | 143 | 144 | //months 145 | char M_arr[12][5] = { { ' ', 'J', 'a', 'n', ' ' }, { ' ', 'F', 'e', 'b', ' ' }, 146 | { ' ', 'M', 'a', 'r', ' ' }, { ' ', 'A', 'p', 'r', ' ' }, { ' ', 'M', 'a', 147 | 'y', ' ' }, { ' ', 'J', 'u', 'n', 'e' }, { ' ', 'J', 'u', 'l', 'y' }, { 148 | ' ', 'A', 'u', 'g', ' ' }, { ' ', 'S', 'e', 'p', 't' }, { ' ', 'O', 'c', 149 | 't', ' ' }, { ' ', 'N', 'o', 'v', ' ' }, { ' ', 'D', 'e', 'c', ' ' } }; 150 | //days 151 | char WT_arr[7][4] = { { 'S', 'u', 'n', ' ' }, { 'M', 'o', 'n', ' ' }, { 'T', 'u', 'e', ' ' }, { 152 | 'W', 'e', 'd', ' ' }, { 'T', 'h', 'u', ' ' }, { 'F', 'r', 'i', ' ' }, { 'S', 'a', 't', ' ' } }; 153 | 154 | // Zeichensatz 5x8 in einer 8x8 Matrix, 0,0 ist rechts oben 155 | unsigned short const font1[96][9] = { 156 | { 0x07, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00 }, // 0x20, Space 157 | { 0x07, 0x04, 0x04, 0x04, 0x04, 0x04, 0x00, 0x04, 0x00 }, // 0x21, ! 158 | { 0x07, 0x09, 0x09, 0x12, 0x00, 0x00, 0x00, 0x00, 0x00 }, // 0x22, " 159 | { 0x07, 0x0a, 0x0a, 0x1f, 0x0a, 0x1f, 0x0a, 0x0a, 0x00 }, // 0x23, # 160 | // { 0x07, 0x04, 0x0f, 0x14, 0x0e, 0x05, 0x1e, 0x04, 0x00 }, // 0x24, $ 161 | { 0x07, 0x06, 0x09, 0x09, 0x06, 0x00, 0x00, 0x00, 0x00 }, // 0x24, $ changed with degree sign 162 | { 0x07, 0x19, 0x19, 0x02, 0x04, 0x08, 0x13, 0x13, 0x00 }, // 0x25, % 163 | { 0x07, 0x04, 0x0a, 0x0a, 0x0a, 0x15, 0x12, 0x0d, 0x00 }, // 0x26, & 164 | { 0x07, 0x04, 0x04, 0x08, 0x00, 0x00, 0x00, 0x00, 0x00 }, // 0x27, ' 165 | { 0x07, 0x02, 0x04, 0x08, 0x08, 0x08, 0x04, 0x02, 0x00 }, // 0x28, ( 166 | { 0x07, 0x08, 0x04, 0x02, 0x02, 0x02, 0x04, 0x08, 0x00 }, // 0x29, ) 167 | { 0x07, 0x04, 0x15, 0x0e, 0x1f, 0x0e, 0x15, 0x04, 0x00 }, // 0x2a, * 168 | { 0x07, 0x00, 0x04, 0x04, 0x1f, 0x04, 0x04, 0x00, 0x00 }, // 0x2b, + 169 | { 0x04, 0x00, 0x00, 0x00, 0x00, 0x00, 0x01, 0x01, 0x02 }, // 0x2c, , 170 | { 0x07, 0x00, 0x00, 0x00, 0x1f, 0x00, 0x00, 0x00, 0x00 }, // 0x2d, - 171 | { 0x04, 0x00, 0x00, 0x00, 0x00, 0x00, 0x03, 0x03, 0x00 }, // 0x2e, . 172 | { 0x07, 0x01, 0x01, 0x02, 0x04, 0x08, 0x10, 0x10, 0x00 }, // 0x2f, / 173 | { 0x07, 0x0e, 0x11, 0x13, 0x15, 0x19, 0x11, 0x0e, 0x00 }, // 0x30, 0 174 | { 0x07, 0x04, 0x0c, 0x04, 0x04, 0x04, 0x04, 0x0e, 0x00 }, // 0x31, 1 175 | { 0x07, 0x0e, 0x11, 0x01, 0x02, 0x04, 0x08, 0x1f, 0x00 }, // 0x32, 2 176 | { 0x07, 0x0e, 0x11, 0x01, 0x06, 0x01, 0x11, 0x0e, 0x00 }, // 0x33, 3 177 | { 0x07, 0x02, 0x06, 0x0a, 0x12, 0x1f, 0x02, 0x02, 0x00 }, // 0x34, 4 178 | { 0x07, 0x1f, 0x10, 0x1e, 0x01, 0x01, 0x11, 0x0e, 0x00 }, // 0x35, 5 179 | { 0x07, 0x06, 0x08, 0x10, 0x1e, 0x11, 0x11, 0x0e, 0x00 }, // 0x36, 6 180 | { 0x07, 0x1f, 0x01, 0x02, 0x04, 0x08, 0x08, 0x08, 0x00 }, // 0x37, 7 181 | { 0x07, 0x0e, 0x11, 0x11, 0x0e, 0x11, 0x11, 0x0e, 0x00 }, // 0x38, 8 182 | { 0x07, 0x0e, 0x11, 0x11, 0x0f, 0x01, 0x02, 0x0c, 0x00 }, // 0x39, 9 183 | { 0x04, 0x00, 0x03, 0x03, 0x00, 0x03, 0x03, 0x00, 0x00 }, // 0x3a, : 184 | { 0x07, 0x00, 0x0c, 0x0c, 0x00, 0x0c, 0x04, 0x08, 0x00 }, // 0x3b, ; 185 | { 0x07, 0x02, 0x04, 0x08, 0x10, 0x08, 0x04, 0x02, 0x00 }, // 0x3c, < 186 | { 0x07, 0x00, 0x00, 0x1f, 0x00, 0x1f, 0x00, 0x00, 0x00 }, // 0x3d, = 187 | { 0x07, 0x08, 0x04, 0x02, 0x01, 0x02, 0x04, 0x08, 0x00 }, // 0x3e, > 188 | { 0x07, 0x0e, 0x11, 0x01, 0x02, 0x04, 0x00, 0x04, 0x00 }, // 0x3f, ? 189 | { 0x07, 0x0e, 0x11, 0x17, 0x15, 0x17, 0x10, 0x0f, 0x00 }, // 0x40, @ 190 | { 0x07, 0x04, 0x0a, 0x11, 0x11, 0x1f, 0x11, 0x11, 0x00 }, // 0x41, A 191 | { 0x07, 0x1e, 0x11, 0x11, 0x1e, 0x11, 0x11, 0x1e, 0x00 }, // 0x42, B 192 | { 0x07, 0x0e, 0x11, 0x10, 0x10, 0x10, 0x11, 0x0e, 0x00 }, // 0x43, C 193 | { 0x07, 0x1e, 0x09, 0x09, 0x09, 0x09, 0x09, 0x1e, 0x00 }, // 0x44, D 194 | { 0x07, 0x1f, 0x10, 0x10, 0x1c, 0x10, 0x10, 0x1f, 0x00 }, // 0x45, E 195 | { 0x07, 0x1f, 0x10, 0x10, 0x1f, 0x10, 0x10, 0x10, 0x00 }, // 0x46, F 196 | { 0x07, 0x0e, 0x11, 0x10, 0x10, 0x13, 0x11, 0x0f, 0x00 }, // 0x37, G 197 | { 0x07, 0x11, 0x11, 0x11, 0x1f, 0x11, 0x11, 0x11, 0x00 }, // 0x48, H 198 | { 0x07, 0x0e, 0x04, 0x04, 0x04, 0x04, 0x04, 0x0e, 0x00 }, // 0x49, I 199 | { 0x07, 0x1f, 0x02, 0x02, 0x02, 0x02, 0x12, 0x0c, 0x00 }, // 0x4a, J 200 | { 0x07, 0x11, 0x12, 0x14, 0x18, 0x14, 0x12, 0x11, 0x00 }, // 0x4b, K 201 | { 0x07, 0x10, 0x10, 0x10, 0x10, 0x10, 0x10, 0x1f, 0x00 }, // 0x4c, L 202 | { 0x07, 0x11, 0x1b, 0x15, 0x11, 0x11, 0x11, 0x11, 0x00 }, // 0x4d, M 203 | { 0x07, 0x11, 0x11, 0x19, 0x15, 0x13, 0x11, 0x11, 0x00 }, // 0x4e, N 204 | { 0x07, 0x0e, 0x11, 0x11, 0x11, 0x11, 0x11, 0x0e, 0x00 }, // 0x4f, O 205 | { 0x07, 0x1e, 0x11, 0x11, 0x1e, 0x10, 0x10, 0x10, 0x00 }, // 0x50, P 206 | { 0x07, 0x0e, 0x11, 0x11, 0x11, 0x15, 0x12, 0x0d, 0x00 }, // 0x51, Q 207 | { 0x07, 0x1e, 0x11, 0x11, 0x1e, 0x14, 0x12, 0x11, 0x00 }, // 0x52, R 208 | { 0x07, 0x0e, 0x11, 0x10, 0x0e, 0x01, 0x11, 0x0e, 0x00 }, // 0x53, S 209 | { 0x07, 0x1f, 0x04, 0x04, 0x04, 0x04, 0x04, 0x04, 0x00 }, // 0x54, T 210 | { 0x07, 0x11, 0x11, 0x11, 0x11, 0x11, 0x11, 0x0e, 0x00 }, // 0x55, U 211 | { 0x07, 0x11, 0x11, 0x11, 0x11, 0x11, 0x0a, 0x04, 0x00 }, // 0x56, V 212 | { 0x07, 0x11, 0x11, 0x11, 0x15, 0x15, 0x1b, 0x11, 0x00 }, // 0x57, W 213 | { 0x07, 0x11, 0x11, 0x0a, 0x04, 0x0a, 0x11, 0x11, 0x00 }, // 0x58, X 214 | { 0x07, 0x11, 0x11, 0x0a, 0x04, 0x04, 0x04, 0x04, 0x00 }, // 0x59, Y 215 | { 0x07, 0x1f, 0x01, 0x02, 0x04, 0x08, 0x10, 0x1f, 0x00 }, // 0x5a, Z 216 | { 0x07, 0x0e, 0x08, 0x08, 0x08, 0x08, 0x08, 0x0e, 0x00 }, // 0x5b, [ 217 | { 0x07, 0x10, 0x10, 0x08, 0x04, 0x02, 0x01, 0x01, 0x00 }, // 0x5c, '\' 218 | { 0x07, 0x0e, 0x02, 0x02, 0x02, 0x02, 0x02, 0x0e, 0x00 }, // 0x5d, ] 219 | { 0x07, 0x04, 0x0a, 0x11, 0x00, 0x00, 0x00, 0x00, 0x00 }, // 0x5e, ^ 220 | { 0x07, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x1f, 0x00 }, // 0x5f, _ 221 | { 0x07, 0x04, 0x04, 0x02, 0x00, 0x00, 0x00, 0x00, 0x00 }, // 0x60, ` 222 | { 0x07, 0x00, 0x0e, 0x01, 0x0d, 0x13, 0x13, 0x0d, 0x00 }, // 0x61, a 223 | { 0x07, 0x10, 0x10, 0x10, 0x1c, 0x12, 0x12, 0x1c, 0x00 }, // 0x62, b 224 | { 0x07, 0x00, 0x00, 0x00, 0x0e, 0x10, 0x10, 0x0e, 0x00 }, // 0x63, c 225 | { 0x07, 0x01, 0x01, 0x01, 0x07, 0x09, 0x09, 0x07, 0x00 }, // 0x64, d 226 | { 0x07, 0x00, 0x00, 0x0e, 0x11, 0x1f, 0x10, 0x0f, 0x00 }, // 0x65, e 227 | { 0x07, 0x06, 0x09, 0x08, 0x1c, 0x08, 0x08, 0x08, 0x00 }, // 0x66, f 228 | { 0x07, 0x00, 0x0e, 0x11, 0x13, 0x0d, 0x01, 0x01, 0x0e }, // 0x67, g 229 | { 0x07, 0x10, 0x10, 0x10, 0x16, 0x19, 0x11, 0x11, 0x00 }, // 0x68, h 230 | { 0x05, 0x00, 0x02, 0x00, 0x06, 0x02, 0x02, 0x07, 0x00 }, // 0x69, i 231 | { 0x07, 0x00, 0x02, 0x00, 0x06, 0x02, 0x02, 0x12, 0x0c }, // 0x6a, j 232 | { 0x07, 0x10, 0x10, 0x12, 0x14, 0x18, 0x14, 0x12, 0x00 }, // 0x6b, k 233 | { 0x05, 0x06, 0x02, 0x02, 0x02, 0x02, 0x02, 0x02, 0x00 }, // 0x6c, l 234 | { 0x07, 0x00, 0x00, 0x0a, 0x15, 0x15, 0x11, 0x11, 0x00 }, // 0x6d, m 235 | { 0x07, 0x00, 0x00, 0x16, 0x19, 0x11, 0x11, 0x11, 0x00 }, // 0x6e, n 236 | { 0x07, 0x00, 0x00, 0x0e, 0x11, 0x11, 0x11, 0x0e, 0x00 }, // 0x6f, o 237 | { 0x07, 0x00, 0x00, 0x1c, 0x12, 0x12, 0x1c, 0x10, 0x10 }, // 0x70, p 238 | { 0x07, 0x00, 0x00, 0x07, 0x09, 0x09, 0x07, 0x01, 0x01 }, // 0x71, q 239 | { 0x07, 0x00, 0x00, 0x16, 0x19, 0x10, 0x10, 0x10, 0x00 }, // 0x72, r 240 | { 0x07, 0x00, 0x00, 0x0f, 0x10, 0x0e, 0x01, 0x1e, 0x00 }, // 0x73, s 241 | { 0x07, 0x08, 0x08, 0x1c, 0x08, 0x08, 0x09, 0x06, 0x00 }, // 0x74, t 242 | { 0x07, 0x00, 0x00, 0x11, 0x11, 0x11, 0x13, 0x0d, 0x00 }, // 0x75, u 243 | { 0x07, 0x00, 0x00, 0x11, 0x11, 0x11, 0x0a, 0x04, 0x00 }, // 0x76, v 244 | { 0x07, 0x00, 0x00, 0x11, 0x11, 0x15, 0x15, 0x0a, 0x00 }, // 0x77, w 245 | { 0x07, 0x00, 0x00, 0x11, 0x0a, 0x04, 0x0a, 0x11, 0x00 }, // 0x78, x 246 | { 0x07, 0x00, 0x00, 0x11, 0x11, 0x0f, 0x01, 0x11, 0x0e }, // 0x79, y 247 | { 0x07, 0x00, 0x00, 0x1f, 0x02, 0x04, 0x08, 0x1f, 0x00 }, // 0x7a, z 248 | { 0x07, 0x06, 0x08, 0x08, 0x10, 0x08, 0x08, 0x06, 0x00 }, // 0x7b, { 249 | { 0x07, 0x04, 0x04, 0x04, 0x00, 0x04, 0x04, 0x04, 0x00 }, // 0x7c, | 250 | { 0x07, 0x0c, 0x02, 0x02, 0x01, 0x02, 0x02, 0x0c, 0x00 }, // 0x7d, } 251 | { 0x07, 0x08, 0x15, 0x02, 0x00, 0x00, 0x00, 0x00, 0x00 }, // 0x7e, ~ 252 | { 0x07, 0x1f, 0x1f, 0x1f, 0x1f, 0x1f, 0x1f, 0x1f, 0x00 } // 0x7f, DEL 253 | }; 254 | //************************************************************************************************** 255 | void connect_to_WiFi() { // We start by connecting to a WiFi network 256 | Serial.println(""); 257 | Serial.print("Connecting to "); 258 | Serial.println(ssid); 259 | 260 | WiFi.mode(WIFI_STA); 261 | WiFi.begin(ssid, pass); 262 | 263 | while (WiFi.status() != WL_CONNECTED) { 264 | delay(500); 265 | Serial.print("."); 266 | } 267 | Serial.println(""); 268 | 269 | Serial.println("WiFi connected"); 270 | Serial.print("IP address: "); 271 | Serial.println(String(WiFi.localIP())); 272 | Serial.println("Starting UDP"); 273 | udp.begin(localPort); 274 | Serial.print("Local port: "); 275 | Serial.println(udp.localPort()); 276 | } 277 | //************************************************************************************************** 278 | tm* connectNTP() { //if response from NTP was succesfull return *tm else return a nullpointer 279 | WiFi.hostByName(ntpServerName, timeServerIP); 280 | Serial.println(timeServerIP); 281 | Serial.println("sending NTP packet..."); 282 | // set all bytes in the buffer to 0 283 | memset(packetBuffer, 0, NTP_PACKET_SIZE); 284 | // Initialize values needed to form NTP request 285 | // (see URL above for details on the packets) 286 | packetBuffer[0] = 0b11100011; // LI, Version, Mode 287 | packetBuffer[1] = 0; // Stratum, or type of clock 288 | packetBuffer[2] = 6; // Polling Interval 289 | packetBuffer[3] = 0xEC; // Peer Clock Precision 290 | // 8 bytes of zero for Root Delay & Root Dispersion 291 | packetBuffer[12] = 49; 292 | packetBuffer[13] = 0x4E; 293 | packetBuffer[14] = 49; 294 | packetBuffer[15] = 52; 295 | // all NTP fields have been given values, now 296 | // you can send a packet requesting a timestamp: 297 | udp.beginPacket(timeServerIP, 123); //NTP requests are to port 123 298 | udp.write(packetBuffer, NTP_PACKET_SIZE); 299 | udp.endPacket(); 300 | delay(1000); // wait to see if a reply is available 301 | int cb = udp.parsePacket(); 302 | udp.read(packetBuffer, NTP_PACKET_SIZE); // read the packet into the buffer 303 | //the timestamp starts at byte 40 of the received packet and is four bytes, 304 | // or two words, long. First, esxtract the two words: 305 | unsigned long highWord = word(packetBuffer[40], packetBuffer[41]); 306 | unsigned long lowWord = word(packetBuffer[42], packetBuffer[43]); 307 | // combine the four bytes (two words) into a long integer 308 | // this is NTP time (seconds since Jan 1 1900): 309 | unsigned long secsSince1900 = highWord << 16 | lowWord; 310 | // now convert NTP time into everyday time: 311 | const unsigned long seventyYears = 2208988800UL; 312 | // subtract seventy years: 313 | epoch = secsSince1900 - seventyYears +2; //+2000ms Verarbeitungszeit 314 | epoch=epoch+3600*corectie; // difference -6h = -6* 3600 sec) 315 | time_t t; 316 | t = epoch; 317 | tm* tt; 318 | tt = localtime(&t); 319 | if (cb == 48) 320 | return (tt); 321 | else 322 | return (NULL); 323 | } 324 | //************************************************************************************************** 325 | void rtc_init(unsigned char sda, unsigned char scl) { 326 | Wire.begin(sda, scl); 327 | rtc_Write(controlREG, 0x00); 328 | } 329 | //************************************************************************************************** 330 | // BCD Code 331 | //************************************************************************************************** 332 | unsigned char dec2bcd(unsigned char x) { //value 0...99 333 | unsigned char z, e, r; 334 | e = x % 10; 335 | z = x / 10; 336 | z = z << 4; 337 | r = e | z; 338 | return (r); 339 | } 340 | unsigned char bcd2dec(unsigned char x) { //value 0...99 341 | int z, e; 342 | e = x & 0x0F; 343 | z = x & 0xF0; 344 | z = z >> 4; 345 | z = z * 10; 346 | return (z + e); 347 | } 348 | //************************************************************************************************** 349 | // RTC I2C Code 350 | //************************************************************************************************** 351 | unsigned char rtc_Read(unsigned char regaddress) { 352 | Wire.beginTransmission(DS3231_ADDRESS); 353 | Wire.write(regaddress); 354 | Wire.endTransmission(); 355 | Wire.requestFrom((unsigned char) DS3231_ADDRESS, (unsigned char) 1); 356 | return (Wire.read()); 357 | } 358 | void rtc_Write(unsigned char regaddress, unsigned char value) { 359 | Wire.beginTransmission(DS3231_ADDRESS); 360 | Wire.write(regaddress); 361 | Wire.write(value); 362 | Wire.endTransmission(); 363 | } 364 | //************************************************************************************************** 365 | unsigned char rtc_sekunde() { 366 | return (bcd2dec(rtc_Read(secondREG))); 367 | } 368 | unsigned char rtc_minute() { 369 | return (bcd2dec(rtc_Read(minuteREG))); 370 | } 371 | unsigned char rtc_stunde() { 372 | return (bcd2dec(rtc_Read(hourREG))); 373 | } 374 | unsigned char rtc_wochentag() { 375 | return (bcd2dec(rtc_Read(WTREG))); 376 | } 377 | unsigned char rtc_tag() { 378 | return (bcd2dec(rtc_Read(dateREG))); 379 | } 380 | unsigned char rtc_monat() { 381 | return (bcd2dec(rtc_Read(monthREG))); 382 | } 383 | unsigned char rtc_jahr() { 384 | return (bcd2dec(rtc_Read(yearREG))); 385 | } 386 | void rtc_sekunde(unsigned char sek) { 387 | rtc_Write(secondREG, (dec2bcd(sek))); 388 | } 389 | void rtc_minute(unsigned char min) { 390 | rtc_Write(minuteREG, (dec2bcd(min))); 391 | } 392 | void rtc_stunde(unsigned char std) { 393 | rtc_Write(hourREG, (dec2bcd(std))); 394 | } 395 | void rtc_wochentag(unsigned char wt) { 396 | rtc_Write(WTREG, (dec2bcd(wt))); 397 | } 398 | void rtc_tag(unsigned char tag) { 399 | rtc_Write(dateREG, (dec2bcd(tag))); 400 | } 401 | void rtc_monat(unsigned char mon) { 402 | rtc_Write(monthREG, (dec2bcd(mon))); 403 | } 404 | void rtc_jahr(unsigned char jahr) { 405 | rtc_Write(yearREG, (dec2bcd(jahr))); 406 | } 407 | //************************************************************************************************** 408 | void rtc_set(tm* tt) { 409 | rtc_sekunde((unsigned char) tt->tm_sec); 410 | rtc_minute((unsigned char) tt->tm_min); 411 | rtc_stunde((unsigned char) tt->tm_hour); 412 | rtc_tag((unsigned char) tt->tm_mday); 413 | rtc_monat((unsigned char) tt->tm_mon + 1); 414 | rtc_jahr((unsigned char) tt->tm_year - 100); 415 | rtc_wochentag((unsigned char) tt->tm_wday); 416 | } 417 | //************************************************************************************************** 418 | float rtc_temp() { 419 | float t = 0.0; 420 | unsigned char lowByte = 0; 421 | signed char highByte = 0; 422 | lowByte = rtc_Read(tempLSBREG); 423 | highByte = rtc_Read(tempMSBREG); 424 | lowByte >>= 6; 425 | lowByte &= 0x03; 426 | t = ((float) lowByte); 427 | t *= 0.25; 428 | t += highByte; 429 | return (t); // return temp value 430 | } 431 | //************************************************************************************************** 432 | void rtc2mez() { 433 | 434 | unsigned short JaZiff; //Jahresziffer 435 | unsigned short JhZiff = 6; //Jahrhundertziffer für 20.Jahrhundert 436 | unsigned short TaZiff; //Tagesziffer 437 | unsigned short WoTag; //Wochentag 438 | unsigned short SJK = 0; //Schaltjahreskorrektur 439 | unsigned short ZDiff; //Zeitdifferenz UTC MEZ/MESZ 440 | unsigned short MoZiff[12] = { 0, 3, 3, 6, 1, 4, 6, 2, 5, 0, 3, 5 }; //Monatsziffer 441 | unsigned short Tage_Monat[12] = { 31, 28, 31, 30, 31, 30, 31, 31, 30, 31, 30, 442 | 31 }; 443 | unsigned short Jahr, Tag, Monat, Stunde, Minute, Sekunde; 444 | //RTC_setMonat(3); 445 | Jahr = rtc_jahr(); 446 | if (Jahr > 99) 447 | Jahr = 0; 448 | Monat = rtc_monat(); 449 | if (Monat > 12) 450 | Monat = 0; 451 | Tag = rtc_tag(); 452 | if (Tag > 31) 453 | Tag = 0; 454 | Stunde = rtc_stunde(); 455 | if (Stunde > 23) 456 | Stunde = 0; 457 | Minute = rtc_minute(); 458 | if (Minute > 59) 459 | Minute = 0; 460 | Sekunde = rtc_sekunde(); 461 | if (Sekunde > 59) 462 | Sekunde = 0; 463 | 464 | JaZiff = ((Jahr + Jahr / 4) % 7); 465 | TaZiff = (Tag % 7); 466 | if ((Jahr % 4) == 0) //Schaltjahr ? 467 | { 468 | Tage_Monat[1] = 29; //dann hat der Febr 29 Tage 469 | if (Monat < 3) 470 | SJK = 6; 471 | else 472 | SJK = 0; 473 | } 474 | WoTag = ((TaZiff + MoZiff[Monat - 1] + JhZiff + JaZiff + SJK) % 7); 475 | 476 | if (Monat < 3 || Monat > 10) 477 | ZDiff = 1; // keine Sommerzeit in Jan, Feb, Nov, Dez 478 | if (Monat > 3 && Monat < 10) 479 | ZDiff = 2; // Sommerz. in Apr, Mai, Jun, Jul, Aug, Sep 480 | if (Monat == 3) { 481 | ZDiff = 1; 482 | if (Tag > 24) //Sommerzeit ab letzten Sonntag des Monats 483 | { 484 | if (Tag == 25) { 485 | if ((Tag + WoTag) < 26) 486 | ZDiff = 2; 487 | } 488 | if (Tag == 26) { 489 | if ((Tag + WoTag) < 28) 490 | ZDiff = 2; 491 | } 492 | if (Tag == 27) { 493 | if ((Tag + WoTag) < 30) 494 | ZDiff = 2; 495 | } 496 | if (Tag == 28) { 497 | if ((Tag + WoTag) < 32) 498 | ZDiff = 2; 499 | } 500 | if (Tag == 29) { 501 | if ((Tag + WoTag) < 34) 502 | ZDiff = 2; 503 | } 504 | if (Tag == 30) { 505 | if ((Tag + WoTag) < 36) 506 | ZDiff = 2; 507 | } 508 | if (Tag == 31) { 509 | if ((Tag + WoTag) < 38) 510 | ZDiff = 2; 511 | } 512 | if ((ZDiff == 2) && (Stunde + 1 < 2) && (WoTag == 0)) 513 | ZDiff = 1; //erst ab 02 Uhr 514 | } 515 | } 516 | if (Monat == 10) { 517 | ZDiff = 2; 518 | if (Tag > 24) //Sommerzeit ab letzten Sonntag des Monats 519 | { 520 | if (Tag == 25) { 521 | if ((Tag + WoTag) < 26) 522 | ZDiff = 1; 523 | } 524 | if (Tag == 26) { 525 | if ((Tag + WoTag) < 28) 526 | ZDiff = 1; 527 | } 528 | if (Tag == 27) { 529 | if ((Tag + WoTag) < 30) 530 | ZDiff = 1; 531 | } 532 | if (Tag == 28) { 533 | if ((Tag + WoTag) < 32) 534 | ZDiff = 1; 535 | } 536 | if (Tag == 29) { 537 | if ((Tag + WoTag) < 34) 538 | ZDiff = 1; 539 | } 540 | if (Tag == 30) { 541 | if ((Tag + WoTag) < 36) 542 | ZDiff = 1; 543 | } 544 | if (Tag == 31) { 545 | if ((Tag + WoTag) < 38) 546 | ZDiff = 1; 547 | } 548 | if ((ZDiff == 1) && (Stunde == 0) && (WoTag == 0)) 549 | ZDiff = 2; //erst ab 02 Uhr 550 | } 551 | } 552 | Stunde = Stunde + ZDiff; 553 | if (Stunde > 23) //Tageskorrektur 554 | { 555 | Stunde = Stunde - 24; //kann 0 oder 1 sein 556 | Tag = Tag + 1; 557 | WoTag = WoTag + 1; 558 | if (Tag > Tage_Monat[Monat - 1]) { 559 | Tag = 1; 560 | Monat = Monat + 1; 561 | if (Monat > 12) { 562 | Monat = 1; 563 | Jahr = Jahr + 1; 564 | } 565 | } 566 | } 567 | MEZ.WT = WoTag; //So=0, Mo=1, Di=2 ... 568 | MEZ.sek1 = Sekunde % 10; 569 | MEZ.sek2 = Sekunde / 10; 570 | MEZ.sek12 = Sekunde; 571 | MEZ.min1 = Minute % 10; 572 | MEZ.min2 = Minute / 10; 573 | MEZ.min12 = Minute; 574 | MEZ.std1 = Stunde % 10; 575 | MEZ.std2 = Stunde / 10; 576 | MEZ.std12 = Stunde; 577 | MEZ.tag12 = Tag; 578 | MEZ.tag1 = Tag % 10; 579 | MEZ.tag2 = Tag / 10; 580 | MEZ.mon12 = Monat; 581 | MEZ.mon1 = Monat % 10; 582 | MEZ.mon2 = Monat / 10; 583 | MEZ.jahr12 = Jahr; 584 | MEZ.jahr1 = Jahr % 10; 585 | MEZ.jahr2 = Jahr / 10; 586 | } 587 | 588 | //************************************************************************************************* 589 | const unsigned short InitArr[7][2] = { { 0x0C, 0x00 }, // display off 590 | { 0x00, 0xFF }, // no LEDtest 591 | { 0x09, 0x00 }, // BCD off 592 | { 0x0F, 0x00 }, // normal operation 593 | { 0x0B, 0x07 }, // start display 594 | { 0x0A, 0x04 }, // brightness 595 | { 0x0C, 0x01 } // display on 596 | }; 597 | //************************************************************************************************** 598 | void max7219_init() //all MAX7219 init 599 | { 600 | unsigned short i, j; 601 | for (i = 0; i < 7; i++) { 602 | digitalWrite(CS, LOW); 603 | delayMicroseconds(1); 604 | for (j = 0; j < anzMAX; j++) { 605 | SPI.write(InitArr[i][0]); //register 606 | SPI.write(InitArr[i][1]); //value 607 | } 608 | digitalWrite(CS, HIGH); 609 | } 610 | } 611 | //************************************************************************************************** 612 | void max7219_set_brightness(unsigned short br) //brightness MAX7219 613 | { 614 | unsigned short j; 615 | if (br < 16) { 616 | digitalWrite(CS, LOW); 617 | delayMicroseconds(1); 618 | for (j = 0; j < anzMAX; j++) { 619 | SPI.write(0x0A); //register 620 | SPI.write(br); //value 621 | } 622 | digitalWrite(CS, HIGH); 623 | } 624 | } 625 | //************************************************************************************************** 626 | void helpArr_init(void) //helperarray init 627 | { 628 | unsigned short i, j, k; 629 | j = 0; 630 | k = 0; 631 | for (i = 0; i < anzMAX * 8; i++) { 632 | helpArrPos[i] = (1 << j); //bitmask 633 | helpArrMAX[i] = k; 634 | j++; 635 | if (j > 7) { 636 | j = 0; 637 | k++; 638 | } 639 | } 640 | } 641 | //************************************************************************************************** 642 | void clear_Display() //clear all 643 | { 644 | unsigned short i, j; 645 | for (i = 0; i < 8; i++) //8 rows 646 | { 647 | digitalWrite(CS, LOW); 648 | delayMicroseconds(1); 649 | for (j = anzMAX; j > 0; j--) { 650 | LEDarr[j - 1][i] = 0; //LEDarr clear 651 | SPI.write(i + 1); //current row 652 | SPI.write(LEDarr[j - 1][i]); 653 | } 654 | digitalWrite(CS, HIGH); 655 | } 656 | } 657 | //********************************************************************************************************* 658 | void rotate_90() // for Generic displays 659 | { 660 | for (uint8_t k = anzMAX; k > 0; k--) { 661 | 662 | uint8_t i, j, m, imask, jmask; 663 | uint8_t tmp[8]={0,0,0,0,0,0,0,0}; 664 | for ( i = 0, imask = 0x01; i < 8; i++, imask <<= 1) { 665 | for (j = 0, jmask = 0x01; j < 8; j++, jmask <<= 1) { 666 | if (LEDarr[k-1][i] & jmask) { 667 | tmp[j] |= imask; 668 | } 669 | } 670 | } 671 | for(m=0; m<8; m++){ 672 | LEDarr[k-1][m]=tmp[m]; 673 | } 674 | } 675 | } 676 | //************************************************************************************************** 677 | void refresh_display() //take info into LEDarr 678 | { 679 | unsigned short i, j; 680 | 681 | #ifdef ROTATE_90 682 | rotate_90(); 683 | #endif 684 | 685 | for (i = 0; i < 8; i++) //8 rows 686 | { 687 | digitalWrite(CS, LOW); 688 | delayMicroseconds(1); 689 | for (j = anzMAX; j > 0; j--) { 690 | SPI.write(i + 1); //current row 691 | 692 | #ifdef REVERSE_HORIZONTAL 693 | SPI.setBitOrder(LSBFIRST); // bitorder for reverse columns 694 | #endif 695 | 696 | #ifdef REVERSE_VERTICAL 697 | SPI.write(LEDarr[j - 1][7-i]); 698 | #else 699 | SPI.write(LEDarr[j - 1][i]); 700 | #endif 701 | 702 | #ifdef REVERSE_HORIZONTAL 703 | SPI.setBitOrder(MSBFIRST); // reset bitorder 704 | #endif 705 | } 706 | digitalWrite(CS, HIGH); 707 | } 708 | } 709 | //************************************************************************************************** 710 | void char2Arr(unsigned short ch, int PosX, short PosY) { //characters into arr 711 | int i, j, k, l, m, o1, o2, o3, o4; //in LEDarr 712 | PosX++; 713 | k = ch - 32; //ASCII position in font 714 | if ((k >= 0) && (k < 96)) //character found in font? 715 | { 716 | o4 = font1[k][0]; //character width 717 | o3 = 1 << (o4 - 2); 718 | for (i = 0; i < o4; i++) { 719 | if (((PosX - i <= maxPosX) && (PosX - i >= 0)) 720 | && ((PosY > -8) && (PosY < 8))) //within matrix? 721 | { 722 | o1 = helpArrPos[PosX - i]; 723 | o2 = helpArrMAX[PosX - i]; 724 | for (j = 0; j < 8; j++) { 725 | if (((PosY >= 0) && (PosY <= j)) || ((PosY < 0) && (j < PosY + 8))) //scroll vertical 726 | { 727 | l = font1[k][j + 1]; 728 | m = (l & (o3 >> i)); //e.g. o4=7 0zzzzz0, o4=4 0zz0 729 | if (m > 0) 730 | LEDarr[o2][j - PosY] = LEDarr[o2][j - PosY] | (o1); //set point 731 | else 732 | LEDarr[o2][j - PosY] = LEDarr[o2][j - PosY] & (~o1); //clear point 733 | } 734 | } 735 | } 736 | } 737 | } 738 | } 739 | 740 | //************************************************************************************************** 741 | void timer50ms() { 742 | static unsigned int cnt50ms = 0; 743 | static unsigned int cnt1s = 0; 744 | static unsigned int cnt1h = 0; 745 | f_tckr50ms = true; 746 | cnt50ms++; 747 | if (cnt50ms == 20) { 748 | f_tckr1s = true; // 1 sec 749 | cnt1s++; 750 | cnt50ms = 0; 751 | } 752 | if (cnt1s == 3600) { // 1h 753 | cnt1h++; 754 | cnt1s = 0; 755 | } 756 | if (cnt1h == 24) { // 1d 757 | f_tckr24h = true; 758 | cnt1h = 0; 759 | } 760 | } 761 | //************************************************************************************************** 762 | // 763 | //The setup function is called once at startup of the sketch 764 | void setup() { 765 | // Add your initialization code here 766 | pinMode(CS, OUTPUT); 767 | digitalWrite(CS, HIGH); 768 | Serial.begin(115200); 769 | dht.begin(); 770 | temperatura = dht.readTemperature(); 771 | umiditate = dht.readHumidity(); 772 | Serial.print(temperatura); 773 | Serial.println("gr.Celsius"); 774 | //rtc.init(SDA, SCL); 775 | SPI.begin(); 776 | helpArr_init(); 777 | max7219_init(); 778 | max7219_set_brightness(0); 779 | rtc_init(SDA, SCL); 780 | clear_Display(); 781 | tckr.attach(0.05, timer50ms); // every 50 msec 782 | connect_to_WiFi(); 783 | tm* tt; 784 | tt = connectNTP(); 785 | if (tt != NULL) 786 | rtc_set(tt); 787 | else 788 | Serial.println("no timepacket received"); 789 | } 790 | //************************************************************************************************** 791 | // The loop function is called in an endless loop 792 | void loop() { 793 | //Add your repeated code here 794 | unsigned int sek1 = 0, sek2 = 0, min1 = 0, min2 = 0, std1 = 0, std2 = 0; 795 | unsigned int sek11 = 0, sek12 = 0, sek21 = 0, sek22 = 0; 796 | unsigned int min11 = 0, min12 = 0, min21 = 0, min22 = 0; 797 | unsigned int std11 = 0, std12 = 0, std21 = 0, std22 = 0; 798 | signed int x = 0; //x1,x2; 799 | signed int y = 0, y1 = 0, y2 = 0; 800 | bool updown = false; 801 | unsigned int sc1 = 0, sc2 = 0, sc3 = 0, sc4 = 0, sc5 = 0, sc6 = 0; 802 | bool f_scrollend_y = false; 803 | unsigned int f_scroll_x = false; 804 | 805 | // temperatura = random(-20,25); 806 | // umiditate = random(1,55); 807 | 808 | 809 | z_PosX = maxPosX; 810 | d_PosX = -8; 811 | // x=0; x1=0; x2=0; 812 | 813 | refresh_display(); 814 | updown = true; 815 | if (updown == false) { 816 | y2 = -9; 817 | y1 = 8; 818 | } 819 | if (updown == true) { //scroll up to down 820 | y2 = 8; 821 | y1 = -8; 822 | } 823 | while (true) { 824 | yield(); 825 | if (f_tckr24h == true) { //syncronisize RTC every day 826 | f_tckr24h = false; 827 | tm* tt; 828 | tt = connectNTP(); 829 | if (tt != NULL) 830 | rtc_set(tt); 831 | else 832 | Serial.println("no timepacket received"); 833 | } 834 | if (f_tckr1s == true) // flag 1sek 835 | { 836 | rtc2mez(); 837 | sek1 = MEZ.sek1; 838 | sek2 = MEZ.sek2; 839 | min1 = MEZ.min1; 840 | min2 = MEZ.min2; 841 | std1 = MEZ.std1; 842 | std2 = MEZ.std2; 843 | y = y2; //scroll updown 844 | sc1 = 1; 845 | sek1++; 846 | if (sek1 == 10) { 847 | sc2 = 1; 848 | sek2++; 849 | sek1 = 0; 850 | } 851 | if (sek2 == 6) { 852 | min1++; 853 | sek2 = 0; 854 | sc3 = 1; 855 | } 856 | if (min1 == 10) { 857 | min2++; 858 | min1 = 0; 859 | sc4 = 1; 860 | } 861 | if (min2 == 6) { 862 | std1++; 863 | min2 = 0; 864 | sc5 = 1; 865 | } 866 | if (std1 == 10) { 867 | std2++; 868 | std1 = 0; 869 | sc6 = 1; 870 | } 871 | if ((std2 == 2) && (std1 == 4)) { 872 | std1 = 0; 873 | std2 = 0; 874 | sc6 = 1; 875 | } 876 | 877 | sek11 = sek12; 878 | sek12 = sek1; 879 | sek21 = sek22; 880 | sek22 = sek2; 881 | min11 = min12; 882 | min12 = min1; 883 | min21 = min22; 884 | min22 = min2; 885 | std11 = std12; 886 | std12 = std1; 887 | std21 = std22; 888 | std22 = std2; 889 | f_tckr1s = false; 890 | if (MEZ.sek12 == 45) 891 | f_scroll_x = true; 892 | if (MEZ.sek12 == 59) 893 | { 894 | temperatura = dht.readTemperature(); 895 | umiditate = dht.readHumidity(); 896 | } 897 | } // end 1s 898 | if (f_tckr50ms == true) { 899 | f_tckr50ms = false; 900 | if (f_scroll_x == true) { 901 | z_PosX++; 902 | d_PosX++; 903 | if (d_PosX == mult) 904 | z_PosX = 0; 905 | if (z_PosX == maxPosX) { 906 | f_scroll_x = false; 907 | d_PosX = -8; 908 | } 909 | } 910 | if (sc1 == 1) { 911 | if (updown == 1) 912 | y--; 913 | else 914 | y++; 915 | char2Arr(48 + sek12, z_PosX - 42, y); 916 | char2Arr(48 + sek11, z_PosX - 42, y + y1); 917 | if (y == 0) { 918 | sc1 = 0; 919 | f_scrollend_y = true; 920 | } 921 | } 922 | else 923 | char2Arr(48 + sek1, z_PosX - 42, 0); 924 | 925 | if (sc2 == 1) { 926 | char2Arr(48 + sek22, z_PosX - 36, y); 927 | char2Arr(48 + sek21, z_PosX - 36, y + y1); 928 | if (y == 0) 929 | sc2 = 0; 930 | } 931 | else 932 | char2Arr(48 + sek2, z_PosX - 36, 0); 933 | 934 | char2Arr(':', z_PosX - 32, 0); 935 | 936 | if (sc3 == 1) { 937 | char2Arr(48 + min12, z_PosX - 25, y); 938 | char2Arr(48 + min11, z_PosX - 25, y + y1); 939 | if (y == 0) 940 | sc3 = 0; 941 | } 942 | else 943 | char2Arr(48 + min1, z_PosX - 25, 0); 944 | 945 | if (sc4 == 1) { 946 | char2Arr(48 + min22, z_PosX - 19, y); 947 | char2Arr(48 + min21, z_PosX - 19, y + y1); 948 | if (y == 0) 949 | sc4 = 0; 950 | } 951 | else 952 | char2Arr(48 + min2, z_PosX - 19, 0); 953 | 954 | char2Arr(':', z_PosX - 15 + x, 0); 955 | 956 | if (sc5 == 1) { 957 | char2Arr(48 + std12, z_PosX - 8, y); 958 | char2Arr(48 + std11, z_PosX - 8, y + y1); 959 | if (y == 0) 960 | sc5 = 0; 961 | } 962 | else 963 | char2Arr(48 + std1, z_PosX - 8, 0); 964 | 965 | if (sc6 == 1) { 966 | char2Arr(48 + std22, z_PosX - 2, y); 967 | char2Arr(48 + std21, z_PosX - 2, y + y1); 968 | if (y == 0) 969 | sc6 = 0; 970 | } 971 | else 972 | char2Arr(48 + std2, z_PosX - 2, 0); 973 | 974 | char2Arr(' ', d_PosX+7, 0); 975 | char2Arr(' ', d_PosX+1, 0); 976 | char2Arr(' ', d_PosX-5, 0); 977 | poz = 11; 978 | char2Arr(WT_arr[MEZ.WT][0], d_PosX - poz, 0); //day of the week 979 | poz = poz+6; 980 | char2Arr(WT_arr[MEZ.WT][1], d_PosX - poz, 0); 981 | poz = poz+6; 982 | char2Arr(WT_arr[MEZ.WT][2], d_PosX - poz, 0); 983 | poz = poz+6; 984 | char2Arr(WT_arr[MEZ.WT][3], d_PosX - poz, 0); 985 | poz = poz+6; 986 | char2Arr(' ', d_PosX - poz, 0); 987 | poz = poz+6; 988 | char2Arr(48 + MEZ.tag2, d_PosX - poz, 0); //day 989 | poz = poz+6; 990 | char2Arr(48 + MEZ.tag1, d_PosX - poz, 0); 991 | poz = poz+6; 992 | char2Arr('- 1', d_PosX - poz, 0); 993 | poz = poz+6; 994 | 995 | char2Arr(M_arr[MEZ.mon12 - 1][1], d_PosX - poz, 0); 996 | poz = poz+6; 997 | char2Arr(M_arr[MEZ.mon12 - 1][2], d_PosX - poz, 0); 998 | poz = poz+6; 999 | char2Arr(M_arr[MEZ.mon12 - 1][3], d_PosX - poz, 0); 1000 | poz = poz+6; 1001 | char2Arr('-', d_PosX - poz, 0); 1002 | poz = poz+6; 1003 | char2Arr('2', d_PosX - poz, 0); //year 1004 | poz = poz+6; 1005 | char2Arr('0', d_PosX - poz, 0); 1006 | poz = poz+6; 1007 | char2Arr(48 + MEZ.jahr2, d_PosX - poz, 0); 1008 | poz = poz+6; 1009 | char2Arr(48 + MEZ.jahr1, d_PosX - poz, 0); 1010 | poz = poz+6; 1011 | char2Arr(' ', d_PosX - poz, 0); 1012 | poz = poz+6; 1013 | char2Arr(' ', d_PosX - poz, 0); 1014 | poz = poz+6; 1015 | char2Arr(' ', d_PosX - poz, 0); 1016 | poz = poz+6; 1017 | 1018 | // Seby part 1019 | if (temperatura >= 10) 1020 | { 1021 | char2Arr('+', d_PosX - poz, 0); //temperature 1022 | poz = poz+6; 1023 | char2Arr(48 + (temperatura / 10), d_PosX - poz, 0); 1024 | poz = poz+6; 1025 | char2Arr(48 + (temperatura % 10), d_PosX - poz, 0); 1026 | poz = poz+6; 1027 | char2Arr('$', d_PosX - poz, 0); 1028 | poz = poz+6; 1029 | char2Arr('C', d_PosX - poz, 0); 1030 | } 1031 | if (temperatura <= 9 && temperatura >0) 1032 | { 1033 | char2Arr(' ', d_PosX - poz, 0); //temperature 1034 | poz = poz+6; 1035 | char2Arr('+', d_PosX - poz, 0); 1036 | poz = poz+6; 1037 | char2Arr(48 + (temperatura % 10), d_PosX - poz, 0); 1038 | poz = poz+6; 1039 | char2Arr('$', d_PosX - poz, 0); 1040 | poz = poz+6; 1041 | char2Arr('C', d_PosX - poz, 0); 1042 | } 1043 | if (temperatura == 0) 1044 | { 1045 | char2Arr(' ', d_PosX - poz, 0); //temperature 1046 | poz = poz+6; 1047 | char2Arr(' ', d_PosX - poz, 0); 1048 | poz = poz+6; 1049 | char2Arr(48 + (temperatura % 10), d_PosX - poz, 0); 1050 | poz = poz+6; 1051 | char2Arr('$', d_PosX - poz, 0); 1052 | poz = poz+6; 1053 | char2Arr('C', d_PosX - poz, 0); 1054 | } 1055 | if (temperatura < 0 && temperatura >= -9) 1056 | { 1057 | char2Arr(' ', d_PosX - poz, 0); //temperature 1058 | poz = poz+6; 1059 | char2Arr('-', d_PosX - poz, 0);//the ,,abs,, turns the negative number into positive 1060 | poz = poz+6; 1061 | char2Arr(48 + (abs(temperatura) % 10), d_PosX - poz, 0); 1062 | poz = poz+6; 1063 | char2Arr('$', d_PosX - poz, 0); 1064 | poz = poz+6; 1065 | char2Arr('C', d_PosX - poz, 0); 1066 | } 1067 | if (temperatura < -9) 1068 | { 1069 | char2Arr('-', d_PosX - poz, 0); //temperature 1070 | poz = poz+6; 1071 | char2Arr(48 + (abs(temperatura) / 10), d_PosX - poz, 0);//the ,,abs,, turns the negative number into positive 1072 | poz = poz+6; 1073 | char2Arr(48 + (abs(temperatura) % 10), d_PosX - poz, 0); 1074 | poz = poz+6; 1075 | char2Arr('$', d_PosX - poz, 0); 1076 | poz = poz+6; 1077 | char2Arr('C', d_PosX - poz, 0); 1078 | } 1079 | poz = poz+6; 1080 | char2Arr(' ', d_PosX - poz, 0); 1081 | poz = poz+6; 1082 | char2Arr(' ', d_PosX - poz, 0); 1083 | 1084 | if (umiditate >= 10) 1085 | { 1086 | poz = poz+6; 1087 | char2Arr(48 + (umiditate / 10), d_PosX - poz, 0); 1088 | poz = poz+6; 1089 | char2Arr(48 + (umiditate % 10), d_PosX - poz, 0); 1090 | poz = poz+6; 1091 | char2Arr('%', d_PosX - poz, 0); 1092 | poz = poz+6; 1093 | char2Arr('R', d_PosX - poz, 0); 1094 | poz = poz+6; 1095 | char2Arr('H', d_PosX - poz, 0); 1096 | } 1097 | if (temperatura <= 9 && temperatura >0) 1098 | { 1099 | poz = poz+6; 1100 | char2Arr(' ', d_PosX - poz, 0); 1101 | poz = poz+6; 1102 | char2Arr(48 + (umiditate), d_PosX - poz, 0); 1103 | poz = poz+6; 1104 | char2Arr('%', d_PosX - poz, 0); 1105 | poz = poz+6; 1106 | char2Arr('R', d_PosX - poz, 0); 1107 | poz = poz+6; 1108 | char2Arr('H', d_PosX - poz, 0); 1109 | } 1110 | poz = poz+6; 1111 | char2Arr(' ', d_PosX - poz, 0); 1112 | poz = poz+6; 1113 | char2Arr(' ', d_PosX - poz, 0); 1114 | poz = poz+6; 1115 | char2Arr(' ', d_PosX - poz, 0); 1116 | //poz = poz+6; 1117 | mult = poz + 5; 1118 | 1119 | // end Seby part 1120 | 1121 | refresh_display(); //alle 50ms 1122 | if (f_scrollend_y == true) { 1123 | f_scrollend_y = false; 1124 | } 1125 | } //end 50ms 1126 | if (y == 0) { 1127 | // do something else 1128 | } 1129 | } //end while(true) 1130 | //this section can not be reached 1131 | } 1132 | -------------------------------------------------------------------------------- /MatrixClock_ESP8266_DHT_3.ino: -------------------------------------------------------------------------------- 1 | //********************************************************************************************************* 2 | //* ESP8266 MatrixClock by Wolle / schreibfaul1 * 3 | //********************************************************************************************************* 4 | // 5 | // first release on 26.02.2017 6 | // updated on 26.03.2019 7 | // Version 1.2.1 8 | // https://github.com/schreibfaul1/ESP8266-LED-Matrix-Clock 9 | // 10 | // THE SOFTWARE IS PROVIDED "AS IS" FOR PRIVATE USE ONLY, IT IS NOT FOR COMMERCIAL USE IN WHOLE OR PART OR CONCEPT. 11 | // FOR PERSONAL USE IT IS SUPPLIED WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE 12 | // WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHOR 13 | // OR COPYRIGHT HOLDER BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR 14 | // OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE 15 | // 16 | // 17 | // ver.0 - small changes by Nicu FLORICA (niq_ro), 31-May_2019 18 | // ver.1 - add DHT sensor for temperature and humidity 19 | // ver.1.a - change at add text to be more easy to change 20 | // ver.2 - change temperature to be as float 21 | // ver.3 - add increase/decrease brightness for day/night & verify NTP time at every hour + work as clock without wifi network (reconnect) 22 | 23 | #include 24 | #include 25 | #include 26 | #include 27 | #include 28 | #include 29 | #include 30 | #include "DHT.h" 31 | 32 | #define SDA 5 // Pin sda (I2C) 33 | #define SCL 4 // Pin scl (I2C) 34 | #define CS 15 // Pin cs (SPI) 35 | #define anzMAX 6 // Anzahl der kaskadierten Module 36 | 37 | char ssid[] = "yourtwifinetkork"; // your network SSID (name) 38 | char pass[] = "password"; // your network password 39 | 40 | // other displays ------------------------------------- 41 | #define REVERSE_HORIZONTAL // Parola, Generic and IC-Station 42 | //#define REVERSE_VERTICAL // IC-Station display 43 | #define ROTATE_90 // Generic display 44 | /* 45 | p A B C D E F G 7 6 5 4 3 2 1 0 G F E D C B A p G F E D C B A p 46 | ------------------------ ------------------------ ------------------------ ------------------------ 47 | 0 |o o o o o o o o| p |o o o o o o o o| 0 |o o o o o o o o| 7 |o o o o o o o o| 48 | 1 |o o o o o o o o| A |o o o o o o o o| 1 |o o o o o o o o| 6 |o o o o o o o o| 49 | 2 |o o o o o o o o| B |o o o o o o o o| 2 |o o o o o o o o| 5 |o o o o o o o o| 50 | 3 |o o o o| C |o o o o| 3 |o o o o| 4 |o o o o| 51 | 4 |o o FC-16 o o| D |o o Generic o o| 4 |o o Parola o o| 3 |o o IC-Station o o| 52 | 5 |o o o o| E |o o o o| 5 |o o o o| 2 |o o o o| 53 | 6 |o o o o o o o o| F |o o o o o o o o| 6 |o o o o o o o o| 1 |o o o o o o o o| 54 | 7 |o o o o o o o o| G |o o o o o o o o| 7 |o o o o o o o o| 0 |o o o o o o o o| 55 | ------------------------ ------------------------ ------------------------ ------------------------ 56 | */ 57 | 58 | // DHT sensor 59 | #define DHTPIN 12 // what pin we're connected to // GPIO 13 = D6 60 | // Uncomment whatever type you're using! 61 | //#define DHTTYPE DHT11 // DHT 11 62 | #define DHTTYPE DHT22 // DHT 22 (AM2302) 63 | //#define DHTTYPE DHT21 // DHT 21 (AM2301) 64 | // Connect pin 1 (on the left) of the sensor to +5V 65 | // NOTE: If using a board with 3.3V logic like an Arduino Due connect pin 1 66 | // to 3.3V instead of 5V! 67 | // Connect pin 2 of the sensor to whatever your DHTPIN is 68 | // Connect pin 4 (on the right) of the sensor to GROUND 69 | // Connect a 10K resistor from pin 2 (data) to pin 1 (power) of the sensor 70 | // Initialize DHT sensor for normal 16mhz Arduino 71 | //DHT dht(DHTPIN, DHTTYPE); 72 | // NOTE: For working with a faster chip, like an Arduino Due or Teensy, you 73 | // might need to increase the threshold for cycle counts considered a 1 or 0. 74 | // You can do this by passing a 3rd parameter for this threshold. It's a bit 75 | // of fiddling to find the right value, but in general the faster the CPU the 76 | // higher the value. The default for a 16mhz AVR is a value of 6. For an 77 | // Arduino Due that runs at 84mhz a value of 30 works. 78 | // Example to initialize DHT sensor for Arduino Due: 79 | DHT dht(DHTPIN, DHTTYPE, 11); // for ESP8266 80 | 81 | 82 | unsigned short maxPosX = anzMAX * 8 - 1; //calculated maxposition 83 | unsigned short LEDarr[anzMAX][8]; //character matrix to display (40*8) 84 | unsigned short helpArrMAX[anzMAX * 8]; //helperarray for chardecoding 85 | unsigned short helpArrPos[anzMAX * 8]; //helperarray pos of chardecoding 86 | unsigned int z_PosX = 0; //xPosition im Display für Zeitanzeige 87 | unsigned int d_PosX = 0; //xPosition im Display f�r Datumanzeige 88 | bool f_tckr1s = false; 89 | bool f_tckr50ms = false; 90 | bool f_tckr24h = false; 91 | unsigned long epoch = 0; 92 | unsigned int localPort = 2390; // local port to listen for UDP packets 93 | const char* ntpServerName = "time.nist.gov"; 94 | const int NTP_PACKET_SIZE = 48; // NTP time stamp is in the first 48 bytes of the message 95 | byte packetBuffer[NTP_PACKET_SIZE]; //buffer to hold incoming and outgoing packets 96 | IPAddress timeServerIP; // time.nist.gov NTP server address 97 | tm *tt, ttm; 98 | #define corectie +1 99 | 100 | float temperatura = 0; 101 | int temp, tempz, tempu, temps, tempr = 0; 102 | byte minus = 0; 103 | int umiditate = 0; 104 | int poz, poz2; 105 | int mult = 0; 106 | byte noapte = 0; 107 | 108 | //Variablen für RTC DS3231 109 | const unsigned char DS3231_ADDRESS = 0x68; 110 | const unsigned char secondREG = 0x00; 111 | const unsigned char minuteREG = 0x01; 112 | const unsigned char hourREG = 0x02; 113 | const unsigned char WTREG = 0x03; //weekday 114 | const unsigned char dateREG = 0x04; 115 | const unsigned char monthREG = 0x05; 116 | const unsigned char yearREG = 0x06; 117 | const unsigned char alarm_min1secREG = 0x07; 118 | const unsigned char alarm_min1minREG = 0x08; 119 | const unsigned char alarm_min1hrREG = 0x09; 120 | const unsigned char alarm_min1dateREG = 0x0A; 121 | const unsigned char alarm_min2minREG = 0x0B; 122 | const unsigned char alarm_min2hrREG = 0x0C; 123 | const unsigned char alarm_min2dateREG = 0x0D; 124 | const unsigned char controlREG = 0x0E; 125 | const unsigned char statusREG = 0x0F; 126 | const unsigned char ageoffsetREG = 0x10; 127 | const unsigned char tempMSBREG = 0x11; 128 | const unsigned char tempLSBREG = 0x12; 129 | const unsigned char _24_hour_format = 0; 130 | const unsigned char _12_hour_format = 1; 131 | const unsigned char AM = 0; 132 | const unsigned char PM = 1; 133 | 134 | struct DateTime { 135 | unsigned short sek1, sek2, sek12, min1, min2, min12, std1, std2, std12; 136 | unsigned short tag1, tag2, tag12, mon1, mon2, mon12, jahr1, jahr2, jahr12, WT; 137 | } MEZ; 138 | 139 | 140 | // The object for the Ticker 141 | Ticker tckr; 142 | // A UDP instance to let us send and receive packets over UDP 143 | WiFiUDP udp; 144 | 145 | 146 | //months 147 | char M_arr[12][5] = { { ' ', 'J', 'a', 'n', ' ' }, { ' ', 'F', 'e', 'b', ' ' }, 148 | { ' ', 'M', 'a', 'r', ' ' }, { ' ', 'A', 'p', 'r', ' ' }, { ' ', 'M', 'a', 149 | 'y', ' ' }, { ' ', 'J', 'u', 'n', 'e' }, { ' ', 'J', 'u', 'l', 'y' }, { 150 | ' ', 'A', 'u', 'g', ' ' }, { ' ', 'S', 'e', 'p', 't' }, { ' ', 'O', 'c', 151 | 't', ' ' }, { ' ', 'N', 'o', 'v', ' ' }, { ' ', 'D', 'e', 'c', ' ' } }; 152 | //days 153 | char WT_arr[7][4] = { { 'S', 'u', 'n', ' ' }, { 'M', 'o', 'n', ' ' }, { 'T', 'u', 'e', ' ' }, { 154 | 'W', 'e', 'd', ' ' }, { 'T', 'h', 'u', ' ' }, { 'F', 'r', 'i', ' ' }, { 'S', 'a', 't', ' ' } }; 155 | 156 | // Zeichensatz 5x8 in einer 8x8 Matrix, 0,0 ist rechts oben 157 | unsigned short const font1[96][9] = { 158 | { 0x07, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00 }, // 0x20, Space 159 | { 0x07, 0x04, 0x04, 0x04, 0x04, 0x04, 0x00, 0x04, 0x00 }, // 0x21, ! 160 | { 0x07, 0x09, 0x09, 0x12, 0x00, 0x00, 0x00, 0x00, 0x00 }, // 0x22, " 161 | { 0x07, 0x0a, 0x0a, 0x1f, 0x0a, 0x1f, 0x0a, 0x0a, 0x00 }, // 0x23, # 162 | // { 0x07, 0x04, 0x0f, 0x14, 0x0e, 0x05, 0x1e, 0x04, 0x00 }, // 0x24, $ 163 | { 0x07, 0x06, 0x09, 0x09, 0x06, 0x00, 0x00, 0x00, 0x00 }, // 0x24, $ changed with degree sign 164 | { 0x07, 0x19, 0x19, 0x02, 0x04, 0x08, 0x13, 0x13, 0x00 }, // 0x25, % 165 | { 0x07, 0x04, 0x0a, 0x0a, 0x0a, 0x15, 0x12, 0x0d, 0x00 }, // 0x26, & 166 | { 0x07, 0x04, 0x04, 0x08, 0x00, 0x00, 0x00, 0x00, 0x00 }, // 0x27, ' 167 | { 0x07, 0x02, 0x04, 0x08, 0x08, 0x08, 0x04, 0x02, 0x00 }, // 0x28, ( 168 | { 0x07, 0x08, 0x04, 0x02, 0x02, 0x02, 0x04, 0x08, 0x00 }, // 0x29, ) 169 | { 0x07, 0x04, 0x15, 0x0e, 0x1f, 0x0e, 0x15, 0x04, 0x00 }, // 0x2a, * 170 | { 0x07, 0x00, 0x04, 0x04, 0x1f, 0x04, 0x04, 0x00, 0x00 }, // 0x2b, + 171 | { 0x04, 0x00, 0x00, 0x00, 0x00, 0x00, 0x01, 0x01, 0x02 }, // 0x2c, , 172 | { 0x07, 0x00, 0x00, 0x00, 0x1f, 0x00, 0x00, 0x00, 0x00 }, // 0x2d, - 173 | { 0x04, 0x00, 0x00, 0x00, 0x00, 0x00, 0x03, 0x03, 0x00 }, // 0x2e, . 174 | { 0x07, 0x01, 0x01, 0x02, 0x04, 0x08, 0x10, 0x10, 0x00 }, // 0x2f, / 175 | { 0x07, 0x0e, 0x11, 0x13, 0x15, 0x19, 0x11, 0x0e, 0x00 }, // 0x30, 0 176 | { 0x07, 0x04, 0x0c, 0x04, 0x04, 0x04, 0x04, 0x0e, 0x00 }, // 0x31, 1 177 | { 0x07, 0x0e, 0x11, 0x01, 0x02, 0x04, 0x08, 0x1f, 0x00 }, // 0x32, 2 178 | { 0x07, 0x0e, 0x11, 0x01, 0x06, 0x01, 0x11, 0x0e, 0x00 }, // 0x33, 3 179 | { 0x07, 0x02, 0x06, 0x0a, 0x12, 0x1f, 0x02, 0x02, 0x00 }, // 0x34, 4 180 | { 0x07, 0x1f, 0x10, 0x1e, 0x01, 0x01, 0x11, 0x0e, 0x00 }, // 0x35, 5 181 | { 0x07, 0x06, 0x08, 0x10, 0x1e, 0x11, 0x11, 0x0e, 0x00 }, // 0x36, 6 182 | { 0x07, 0x1f, 0x01, 0x02, 0x04, 0x08, 0x08, 0x08, 0x00 }, // 0x37, 7 183 | { 0x07, 0x0e, 0x11, 0x11, 0x0e, 0x11, 0x11, 0x0e, 0x00 }, // 0x38, 8 184 | { 0x07, 0x0e, 0x11, 0x11, 0x0f, 0x01, 0x02, 0x0c, 0x00 }, // 0x39, 9 185 | { 0x04, 0x00, 0x03, 0x03, 0x00, 0x03, 0x03, 0x00, 0x00 }, // 0x3a, : 186 | { 0x07, 0x00, 0x0c, 0x0c, 0x00, 0x0c, 0x04, 0x08, 0x00 }, // 0x3b, ; 187 | { 0x07, 0x02, 0x04, 0x08, 0x10, 0x08, 0x04, 0x02, 0x00 }, // 0x3c, < 188 | { 0x07, 0x00, 0x00, 0x1f, 0x00, 0x1f, 0x00, 0x00, 0x00 }, // 0x3d, = 189 | { 0x07, 0x08, 0x04, 0x02, 0x01, 0x02, 0x04, 0x08, 0x00 }, // 0x3e, > 190 | { 0x07, 0x0e, 0x11, 0x01, 0x02, 0x04, 0x00, 0x04, 0x00 }, // 0x3f, ? 191 | { 0x07, 0x0e, 0x11, 0x17, 0x15, 0x17, 0x10, 0x0f, 0x00 }, // 0x40, @ 192 | { 0x07, 0x04, 0x0a, 0x11, 0x11, 0x1f, 0x11, 0x11, 0x00 }, // 0x41, A 193 | { 0x07, 0x1e, 0x11, 0x11, 0x1e, 0x11, 0x11, 0x1e, 0x00 }, // 0x42, B 194 | { 0x07, 0x0e, 0x11, 0x10, 0x10, 0x10, 0x11, 0x0e, 0x00 }, // 0x43, C 195 | { 0x07, 0x1e, 0x09, 0x09, 0x09, 0x09, 0x09, 0x1e, 0x00 }, // 0x44, D 196 | { 0x07, 0x1f, 0x10, 0x10, 0x1c, 0x10, 0x10, 0x1f, 0x00 }, // 0x45, E 197 | { 0x07, 0x1f, 0x10, 0x10, 0x1f, 0x10, 0x10, 0x10, 0x00 }, // 0x46, F 198 | { 0x07, 0x0e, 0x11, 0x10, 0x10, 0x13, 0x11, 0x0f, 0x00 }, // 0x37, G 199 | { 0x07, 0x11, 0x11, 0x11, 0x1f, 0x11, 0x11, 0x11, 0x00 }, // 0x48, H 200 | { 0x07, 0x0e, 0x04, 0x04, 0x04, 0x04, 0x04, 0x0e, 0x00 }, // 0x49, I 201 | { 0x07, 0x1f, 0x02, 0x02, 0x02, 0x02, 0x12, 0x0c, 0x00 }, // 0x4a, J 202 | { 0x07, 0x11, 0x12, 0x14, 0x18, 0x14, 0x12, 0x11, 0x00 }, // 0x4b, K 203 | { 0x07, 0x10, 0x10, 0x10, 0x10, 0x10, 0x10, 0x1f, 0x00 }, // 0x4c, L 204 | { 0x07, 0x11, 0x1b, 0x15, 0x11, 0x11, 0x11, 0x11, 0x00 }, // 0x4d, M 205 | { 0x07, 0x11, 0x11, 0x19, 0x15, 0x13, 0x11, 0x11, 0x00 }, // 0x4e, N 206 | { 0x07, 0x0e, 0x11, 0x11, 0x11, 0x11, 0x11, 0x0e, 0x00 }, // 0x4f, O 207 | { 0x07, 0x1e, 0x11, 0x11, 0x1e, 0x10, 0x10, 0x10, 0x00 }, // 0x50, P 208 | { 0x07, 0x0e, 0x11, 0x11, 0x11, 0x15, 0x12, 0x0d, 0x00 }, // 0x51, Q 209 | { 0x07, 0x1e, 0x11, 0x11, 0x1e, 0x14, 0x12, 0x11, 0x00 }, // 0x52, R 210 | { 0x07, 0x0e, 0x11, 0x10, 0x0e, 0x01, 0x11, 0x0e, 0x00 }, // 0x53, S 211 | { 0x07, 0x1f, 0x04, 0x04, 0x04, 0x04, 0x04, 0x04, 0x00 }, // 0x54, T 212 | { 0x07, 0x11, 0x11, 0x11, 0x11, 0x11, 0x11, 0x0e, 0x00 }, // 0x55, U 213 | { 0x07, 0x11, 0x11, 0x11, 0x11, 0x11, 0x0a, 0x04, 0x00 }, // 0x56, V 214 | { 0x07, 0x11, 0x11, 0x11, 0x15, 0x15, 0x1b, 0x11, 0x00 }, // 0x57, W 215 | { 0x07, 0x11, 0x11, 0x0a, 0x04, 0x0a, 0x11, 0x11, 0x00 }, // 0x58, X 216 | { 0x07, 0x11, 0x11, 0x0a, 0x04, 0x04, 0x04, 0x04, 0x00 }, // 0x59, Y 217 | { 0x07, 0x1f, 0x01, 0x02, 0x04, 0x08, 0x10, 0x1f, 0x00 }, // 0x5a, Z 218 | { 0x07, 0x0e, 0x08, 0x08, 0x08, 0x08, 0x08, 0x0e, 0x00 }, // 0x5b, [ 219 | { 0x07, 0x10, 0x10, 0x08, 0x04, 0x02, 0x01, 0x01, 0x00 }, // 0x5c, '\' 220 | { 0x07, 0x0e, 0x02, 0x02, 0x02, 0x02, 0x02, 0x0e, 0x00 }, // 0x5d, ] 221 | { 0x07, 0x04, 0x0a, 0x11, 0x00, 0x00, 0x00, 0x00, 0x00 }, // 0x5e, ^ 222 | { 0x07, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x1f, 0x00 }, // 0x5f, _ 223 | { 0x07, 0x04, 0x04, 0x02, 0x00, 0x00, 0x00, 0x00, 0x00 }, // 0x60, ` 224 | { 0x07, 0x00, 0x0e, 0x01, 0x0d, 0x13, 0x13, 0x0d, 0x00 }, // 0x61, a 225 | { 0x07, 0x10, 0x10, 0x10, 0x1c, 0x12, 0x12, 0x1c, 0x00 }, // 0x62, b 226 | { 0x07, 0x00, 0x00, 0x00, 0x0e, 0x10, 0x10, 0x0e, 0x00 }, // 0x63, c 227 | { 0x07, 0x01, 0x01, 0x01, 0x07, 0x09, 0x09, 0x07, 0x00 }, // 0x64, d 228 | { 0x07, 0x00, 0x00, 0x0e, 0x11, 0x1f, 0x10, 0x0f, 0x00 }, // 0x65, e 229 | { 0x07, 0x06, 0x09, 0x08, 0x1c, 0x08, 0x08, 0x08, 0x00 }, // 0x66, f 230 | { 0x07, 0x00, 0x0e, 0x11, 0x13, 0x0d, 0x01, 0x01, 0x0e }, // 0x67, g 231 | { 0x07, 0x10, 0x10, 0x10, 0x16, 0x19, 0x11, 0x11, 0x00 }, // 0x68, h 232 | { 0x05, 0x00, 0x02, 0x00, 0x06, 0x02, 0x02, 0x07, 0x00 }, // 0x69, i 233 | { 0x07, 0x00, 0x02, 0x00, 0x06, 0x02, 0x02, 0x12, 0x0c }, // 0x6a, j 234 | { 0x07, 0x10, 0x10, 0x12, 0x14, 0x18, 0x14, 0x12, 0x00 }, // 0x6b, k 235 | { 0x05, 0x06, 0x02, 0x02, 0x02, 0x02, 0x02, 0x02, 0x00 }, // 0x6c, l 236 | { 0x07, 0x00, 0x00, 0x0a, 0x15, 0x15, 0x11, 0x11, 0x00 }, // 0x6d, m 237 | { 0x07, 0x00, 0x00, 0x16, 0x19, 0x11, 0x11, 0x11, 0x00 }, // 0x6e, n 238 | { 0x07, 0x00, 0x00, 0x0e, 0x11, 0x11, 0x11, 0x0e, 0x00 }, // 0x6f, o 239 | { 0x07, 0x00, 0x00, 0x1c, 0x12, 0x12, 0x1c, 0x10, 0x10 }, // 0x70, p 240 | { 0x07, 0x00, 0x00, 0x07, 0x09, 0x09, 0x07, 0x01, 0x01 }, // 0x71, q 241 | { 0x07, 0x00, 0x00, 0x16, 0x19, 0x10, 0x10, 0x10, 0x00 }, // 0x72, r 242 | { 0x07, 0x00, 0x00, 0x0f, 0x10, 0x0e, 0x01, 0x1e, 0x00 }, // 0x73, s 243 | { 0x07, 0x08, 0x08, 0x1c, 0x08, 0x08, 0x09, 0x06, 0x00 }, // 0x74, t 244 | { 0x07, 0x00, 0x00, 0x11, 0x11, 0x11, 0x13, 0x0d, 0x00 }, // 0x75, u 245 | { 0x07, 0x00, 0x00, 0x11, 0x11, 0x11, 0x0a, 0x04, 0x00 }, // 0x76, v 246 | { 0x07, 0x00, 0x00, 0x11, 0x11, 0x15, 0x15, 0x0a, 0x00 }, // 0x77, w 247 | { 0x07, 0x00, 0x00, 0x11, 0x0a, 0x04, 0x0a, 0x11, 0x00 }, // 0x78, x 248 | { 0x07, 0x00, 0x00, 0x11, 0x11, 0x0f, 0x01, 0x11, 0x0e }, // 0x79, y 249 | { 0x07, 0x00, 0x00, 0x1f, 0x02, 0x04, 0x08, 0x1f, 0x00 }, // 0x7a, z 250 | { 0x07, 0x06, 0x08, 0x08, 0x10, 0x08, 0x08, 0x06, 0x00 }, // 0x7b, { 251 | { 0x07, 0x04, 0x04, 0x04, 0x00, 0x04, 0x04, 0x04, 0x00 }, // 0x7c, | 252 | { 0x07, 0x0c, 0x02, 0x02, 0x01, 0x02, 0x02, 0x0c, 0x00 }, // 0x7d, } 253 | { 0x07, 0x08, 0x15, 0x02, 0x00, 0x00, 0x00, 0x00, 0x00 }, // 0x7e, ~ 254 | { 0x07, 0x1f, 0x1f, 0x1f, 0x1f, 0x1f, 0x1f, 0x1f, 0x00 } // 0x7f, DEL 255 | }; 256 | //************************************************************************************************** 257 | void connect_to_WiFi() { // We start by connecting to a WiFi network 258 | Serial.println(""); 259 | Serial.print("Connecting to "); 260 | Serial.println(ssid); 261 | 262 | WiFi.mode(WIFI_STA); 263 | WiFi.begin(ssid, pass); 264 | /* 265 | while (WiFi.status() != WL_CONNECTED) { 266 | delay(500); 267 | Serial.print("."); 268 | } 269 | */ 270 | for (byte i = 0; i <= 50; i++) 271 | { 272 | if (WiFi.status() != WL_CONNECTED) 273 | { 274 | delay(500); 275 | Serial.print("."); 276 | } 277 | else 278 | i = 50; 279 | } 280 | if (WiFi.status() == WL_CONNECTED) 281 | { 282 | Serial.println("WiFi connected"); 283 | Serial.print("IP address: "); 284 | Serial.println(String(WiFi.localIP())); 285 | Serial.println("Starting UDP"); 286 | udp.begin(localPort); 287 | Serial.print("Local port: "); 288 | Serial.println(udp.localPort()); 289 | } 290 | } 291 | //************************************************************************************************** 292 | tm* connectNTP() { //if response from NTP was succesfull return *tm else return a nullpointer 293 | WiFi.hostByName(ntpServerName, timeServerIP); 294 | Serial.println(timeServerIP); 295 | Serial.println("sending NTP packet..."); 296 | // set all bytes in the buffer to 0 297 | memset(packetBuffer, 0, NTP_PACKET_SIZE); 298 | // Initialize values needed to form NTP request 299 | // (see URL above for details on the packets) 300 | packetBuffer[0] = 0b11100011; // LI, Version, Mode 301 | packetBuffer[1] = 0; // Stratum, or type of clock 302 | packetBuffer[2] = 6; // Polling Interval 303 | packetBuffer[3] = 0xEC; // Peer Clock Precision 304 | // 8 bytes of zero for Root Delay & Root Dispersion 305 | packetBuffer[12] = 49; 306 | packetBuffer[13] = 0x4E; 307 | packetBuffer[14] = 49; 308 | packetBuffer[15] = 52; 309 | // all NTP fields have been given values, now 310 | // you can send a packet requesting a timestamp: 311 | udp.beginPacket(timeServerIP, 123); //NTP requests are to port 123 312 | udp.write(packetBuffer, NTP_PACKET_SIZE); 313 | udp.endPacket(); 314 | delay(1000); // wait to see if a reply is available 315 | int cb = udp.parsePacket(); 316 | udp.read(packetBuffer, NTP_PACKET_SIZE); // read the packet into the buffer 317 | //the timestamp starts at byte 40 of the received packet and is four bytes, 318 | // or two words, long. First, esxtract the two words: 319 | unsigned long highWord = word(packetBuffer[40], packetBuffer[41]); 320 | unsigned long lowWord = word(packetBuffer[42], packetBuffer[43]); 321 | // combine the four bytes (two words) into a long integer 322 | // this is NTP time (seconds since Jan 1 1900): 323 | unsigned long secsSince1900 = highWord << 16 | lowWord; 324 | // now convert NTP time into everyday time: 325 | const unsigned long seventyYears = 2208988800UL; 326 | // subtract seventy years: 327 | epoch = secsSince1900 - seventyYears +2; //+2000ms Verarbeitungszeit 328 | epoch=epoch+3600*corectie; // difference -6h = -6* 3600 sec) 329 | time_t t; 330 | t = epoch; 331 | tm* tt; 332 | tt = localtime(&t); 333 | if (cb == 48) 334 | return (tt); 335 | else 336 | return (NULL); 337 | } 338 | //************************************************************************************************** 339 | void rtc_init(unsigned char sda, unsigned char scl) { 340 | Wire.begin(sda, scl); 341 | rtc_Write(controlREG, 0x00); 342 | } 343 | //************************************************************************************************** 344 | // BCD Code 345 | //************************************************************************************************** 346 | unsigned char dec2bcd(unsigned char x) { //value 0...99 347 | unsigned char z, e, r; 348 | e = x % 10; 349 | z = x / 10; 350 | z = z << 4; 351 | r = e | z; 352 | return (r); 353 | } 354 | unsigned char bcd2dec(unsigned char x) { //value 0...99 355 | int z, e; 356 | e = x & 0x0F; 357 | z = x & 0xF0; 358 | z = z >> 4; 359 | z = z * 10; 360 | return (z + e); 361 | } 362 | //************************************************************************************************** 363 | // RTC I2C Code 364 | //************************************************************************************************** 365 | unsigned char rtc_Read(unsigned char regaddress) { 366 | Wire.beginTransmission(DS3231_ADDRESS); 367 | Wire.write(regaddress); 368 | Wire.endTransmission(); 369 | Wire.requestFrom((unsigned char) DS3231_ADDRESS, (unsigned char) 1); 370 | return (Wire.read()); 371 | } 372 | void rtc_Write(unsigned char regaddress, unsigned char value) { 373 | Wire.beginTransmission(DS3231_ADDRESS); 374 | Wire.write(regaddress); 375 | Wire.write(value); 376 | Wire.endTransmission(); 377 | } 378 | //************************************************************************************************** 379 | unsigned char rtc_sekunde() { 380 | return (bcd2dec(rtc_Read(secondREG))); 381 | } 382 | unsigned char rtc_minute() { 383 | return (bcd2dec(rtc_Read(minuteREG))); 384 | } 385 | unsigned char rtc_stunde() { 386 | return (bcd2dec(rtc_Read(hourREG))); 387 | } 388 | unsigned char rtc_wochentag() { 389 | return (bcd2dec(rtc_Read(WTREG))); 390 | } 391 | unsigned char rtc_tag() { 392 | return (bcd2dec(rtc_Read(dateREG))); 393 | } 394 | unsigned char rtc_monat() { 395 | return (bcd2dec(rtc_Read(monthREG))); 396 | } 397 | unsigned char rtc_jahr() { 398 | return (bcd2dec(rtc_Read(yearREG))); 399 | } 400 | void rtc_sekunde(unsigned char sek) { 401 | rtc_Write(secondREG, (dec2bcd(sek))); 402 | } 403 | void rtc_minute(unsigned char min) { 404 | rtc_Write(minuteREG, (dec2bcd(min))); 405 | } 406 | void rtc_stunde(unsigned char std) { 407 | rtc_Write(hourREG, (dec2bcd(std))); 408 | } 409 | void rtc_wochentag(unsigned char wt) { 410 | rtc_Write(WTREG, (dec2bcd(wt))); 411 | } 412 | void rtc_tag(unsigned char tag) { 413 | rtc_Write(dateREG, (dec2bcd(tag))); 414 | } 415 | void rtc_monat(unsigned char mon) { 416 | rtc_Write(monthREG, (dec2bcd(mon))); 417 | } 418 | void rtc_jahr(unsigned char jahr) { 419 | rtc_Write(yearREG, (dec2bcd(jahr))); 420 | } 421 | //************************************************************************************************** 422 | void rtc_set(tm* tt) { 423 | rtc_sekunde((unsigned char) tt->tm_sec); 424 | rtc_minute((unsigned char) tt->tm_min); 425 | rtc_stunde((unsigned char) tt->tm_hour); 426 | rtc_tag((unsigned char) tt->tm_mday); 427 | rtc_monat((unsigned char) tt->tm_mon + 1); 428 | rtc_jahr((unsigned char) tt->tm_year - 100); 429 | rtc_wochentag((unsigned char) tt->tm_wday); 430 | Serial.println("adjust the clock !"); 431 | } 432 | //************************************************************************************************** 433 | float rtc_temp() { 434 | float t = 0.0; 435 | unsigned char lowByte = 0; 436 | signed char highByte = 0; 437 | lowByte = rtc_Read(tempLSBREG); 438 | highByte = rtc_Read(tempMSBREG); 439 | lowByte >>= 6; 440 | lowByte &= 0x03; 441 | t = ((float) lowByte); 442 | t *= 0.25; 443 | t += highByte; 444 | return (t); // return temp value 445 | } 446 | //************************************************************************************************** 447 | void rtc2mez() { 448 | 449 | unsigned short JaZiff; //Jahresziffer 450 | unsigned short JhZiff = 6; //Jahrhundertziffer für 20.Jahrhundert 451 | unsigned short TaZiff; //Tagesziffer 452 | unsigned short WoTag; //Wochentag 453 | unsigned short SJK = 0; //Schaltjahreskorrektur 454 | unsigned short ZDiff; //Zeitdifferenz UTC MEZ/MESZ 455 | unsigned short MoZiff[12] = { 0, 3, 3, 6, 1, 4, 6, 2, 5, 0, 3, 5 }; //Monatsziffer 456 | unsigned short Tage_Monat[12] = { 31, 28, 31, 30, 31, 30, 31, 31, 30, 31, 30, 457 | 31 }; 458 | unsigned short Jahr, Tag, Monat, Stunde, Minute, Sekunde; 459 | //RTC_setMonat(3); 460 | Jahr = rtc_jahr(); 461 | if (Jahr > 99) 462 | Jahr = 0; 463 | Monat = rtc_monat(); 464 | if (Monat > 12) 465 | Monat = 0; 466 | Tag = rtc_tag(); 467 | if (Tag > 31) 468 | Tag = 0; 469 | Stunde = rtc_stunde(); 470 | if (Stunde > 23) 471 | Stunde = 0; 472 | Minute = rtc_minute(); 473 | if (Minute > 59) 474 | Minute = 0; 475 | Sekunde = rtc_sekunde(); 476 | if (Sekunde > 59) 477 | Sekunde = 0; 478 | 479 | JaZiff = ((Jahr + Jahr / 4) % 7); 480 | TaZiff = (Tag % 7); 481 | if ((Jahr % 4) == 0) //Schaltjahr ? 482 | { 483 | Tage_Monat[1] = 29; //dann hat der Febr 29 Tage 484 | if (Monat < 3) 485 | SJK = 6; 486 | else 487 | SJK = 0; 488 | } 489 | WoTag = ((TaZiff + MoZiff[Monat - 1] + JhZiff + JaZiff + SJK) % 7); 490 | 491 | if (Monat < 3 || Monat > 10) 492 | ZDiff = 1; // keine Sommerzeit in Jan, Feb, Nov, Dez 493 | if (Monat > 3 && Monat < 10) 494 | ZDiff = 2; // Sommerz. in Apr, Mai, Jun, Jul, Aug, Sep 495 | if (Monat == 3) { 496 | ZDiff = 1; 497 | if (Tag > 24) //Sommerzeit ab letzten Sonntag des Monats 498 | { 499 | if (Tag == 25) { 500 | if ((Tag + WoTag) < 26) 501 | ZDiff = 2; 502 | } 503 | if (Tag == 26) { 504 | if ((Tag + WoTag) < 28) 505 | ZDiff = 2; 506 | } 507 | if (Tag == 27) { 508 | if ((Tag + WoTag) < 30) 509 | ZDiff = 2; 510 | } 511 | if (Tag == 28) { 512 | if ((Tag + WoTag) < 32) 513 | ZDiff = 2; 514 | } 515 | if (Tag == 29) { 516 | if ((Tag + WoTag) < 34) 517 | ZDiff = 2; 518 | } 519 | if (Tag == 30) { 520 | if ((Tag + WoTag) < 36) 521 | ZDiff = 2; 522 | } 523 | if (Tag == 31) { 524 | if ((Tag + WoTag) < 38) 525 | ZDiff = 2; 526 | } 527 | if ((ZDiff == 2) && (Stunde + 1 < 2) && (WoTag == 0)) 528 | ZDiff = 1; //erst ab 02 Uhr 529 | } 530 | } 531 | if (Monat == 10) { 532 | ZDiff = 2; 533 | if (Tag > 24) //Sommerzeit ab letzten Sonntag des Monats 534 | { 535 | if (Tag == 25) { 536 | if ((Tag + WoTag) < 26) 537 | ZDiff = 1; 538 | } 539 | if (Tag == 26) { 540 | if ((Tag + WoTag) < 28) 541 | ZDiff = 1; 542 | } 543 | if (Tag == 27) { 544 | if ((Tag + WoTag) < 30) 545 | ZDiff = 1; 546 | } 547 | if (Tag == 28) { 548 | if ((Tag + WoTag) < 32) 549 | ZDiff = 1; 550 | } 551 | if (Tag == 29) { 552 | if ((Tag + WoTag) < 34) 553 | ZDiff = 1; 554 | } 555 | if (Tag == 30) { 556 | if ((Tag + WoTag) < 36) 557 | ZDiff = 1; 558 | } 559 | if (Tag == 31) { 560 | if ((Tag + WoTag) < 38) 561 | ZDiff = 1; 562 | } 563 | if ((ZDiff == 1) && (Stunde == 0) && (WoTag == 0)) 564 | ZDiff = 2; //erst ab 02 Uhr 565 | } 566 | } 567 | Stunde = Stunde + ZDiff; 568 | if (Stunde > 23) //Tageskorrektur 569 | { 570 | Stunde = Stunde - 24; //kann 0 oder 1 sein 571 | Tag = Tag + 1; 572 | WoTag = WoTag + 1; 573 | if (Tag > Tage_Monat[Monat - 1]) { 574 | Tag = 1; 575 | Monat = Monat + 1; 576 | if (Monat > 12) { 577 | Monat = 1; 578 | Jahr = Jahr + 1; 579 | } 580 | } 581 | } 582 | MEZ.WT = WoTag; //So=0, Mo=1, Di=2 ... 583 | MEZ.sek1 = Sekunde % 10; 584 | MEZ.sek2 = Sekunde / 10; 585 | MEZ.sek12 = Sekunde; 586 | MEZ.min1 = Minute % 10; 587 | MEZ.min2 = Minute / 10; 588 | MEZ.min12 = Minute; 589 | MEZ.std1 = Stunde % 10; 590 | MEZ.std2 = Stunde / 10; 591 | MEZ.std12 = Stunde; 592 | MEZ.tag12 = Tag; 593 | MEZ.tag1 = Tag % 10; 594 | MEZ.tag2 = Tag / 10; 595 | MEZ.mon12 = Monat; 596 | MEZ.mon1 = Monat % 10; 597 | MEZ.mon2 = Monat / 10; 598 | MEZ.jahr12 = Jahr; 599 | MEZ.jahr1 = Jahr % 10; 600 | MEZ.jahr2 = Jahr / 10; 601 | } 602 | 603 | //************************************************************************************************* 604 | const unsigned short InitArr[7][2] = { { 0x0C, 0x00 }, // display off 605 | { 0x00, 0xFF }, // no LEDtest 606 | { 0x09, 0x00 }, // BCD off 607 | { 0x0F, 0x00 }, // normal operation 608 | { 0x0B, 0x07 }, // start display 609 | { 0x0A, 0x04 }, // brightness 610 | { 0x0C, 0x01 } // display on 611 | }; 612 | //************************************************************************************************** 613 | void max7219_init() //all MAX7219 init 614 | { 615 | unsigned short i, j; 616 | for (i = 0; i < 7; i++) { 617 | digitalWrite(CS, LOW); 618 | delayMicroseconds(1); 619 | for (j = 0; j < anzMAX; j++) { 620 | SPI.write(InitArr[i][0]); //register 621 | SPI.write(InitArr[i][1]); //value 622 | } 623 | digitalWrite(CS, HIGH); 624 | } 625 | } 626 | //************************************************************************************************** 627 | void max7219_set_brightness(unsigned short br) //brightness MAX7219 628 | { 629 | unsigned short j; 630 | if (br < 16) { 631 | digitalWrite(CS, LOW); 632 | delayMicroseconds(1); 633 | for (j = 0; j < anzMAX; j++) { 634 | SPI.write(0x0A); //register 635 | SPI.write(br); //value 636 | } 637 | digitalWrite(CS, HIGH); 638 | } 639 | } 640 | //************************************************************************************************** 641 | void helpArr_init(void) //helperarray init 642 | { 643 | unsigned short i, j, k; 644 | j = 0; 645 | k = 0; 646 | for (i = 0; i < anzMAX * 8; i++) { 647 | helpArrPos[i] = (1 << j); //bitmask 648 | helpArrMAX[i] = k; 649 | j++; 650 | if (j > 7) { 651 | j = 0; 652 | k++; 653 | } 654 | } 655 | } 656 | //************************************************************************************************** 657 | void clear_Display() //clear all 658 | { 659 | unsigned short i, j; 660 | for (i = 0; i < 8; i++) //8 rows 661 | { 662 | digitalWrite(CS, LOW); 663 | delayMicroseconds(1); 664 | for (j = anzMAX; j > 0; j--) { 665 | LEDarr[j - 1][i] = 0; //LEDarr clear 666 | SPI.write(i + 1); //current row 667 | SPI.write(LEDarr[j - 1][i]); 668 | } 669 | digitalWrite(CS, HIGH); 670 | } 671 | } 672 | //********************************************************************************************************* 673 | void rotate_90() // for Generic displays 674 | { 675 | for (uint8_t k = anzMAX; k > 0; k--) { 676 | 677 | uint8_t i, j, m, imask, jmask; 678 | uint8_t tmp[8]={0,0,0,0,0,0,0,0}; 679 | for ( i = 0, imask = 0x01; i < 8; i++, imask <<= 1) { 680 | for (j = 0, jmask = 0x01; j < 8; j++, jmask <<= 1) { 681 | if (LEDarr[k-1][i] & jmask) { 682 | tmp[j] |= imask; 683 | } 684 | } 685 | } 686 | for(m=0; m<8; m++){ 687 | LEDarr[k-1][m]=tmp[m]; 688 | } 689 | } 690 | } 691 | //************************************************************************************************** 692 | void refresh_display() //take info into LEDarr 693 | { 694 | unsigned short i, j; 695 | 696 | #ifdef ROTATE_90 697 | rotate_90(); 698 | #endif 699 | 700 | for (i = 0; i < 8; i++) //8 rows 701 | { 702 | digitalWrite(CS, LOW); 703 | delayMicroseconds(1); 704 | for (j = anzMAX; j > 0; j--) { 705 | SPI.write(i + 1); //current row 706 | 707 | #ifdef REVERSE_HORIZONTAL 708 | SPI.setBitOrder(LSBFIRST); // bitorder for reverse columns 709 | #endif 710 | 711 | #ifdef REVERSE_VERTICAL 712 | SPI.write(LEDarr[j - 1][7-i]); 713 | #else 714 | SPI.write(LEDarr[j - 1][i]); 715 | #endif 716 | 717 | #ifdef REVERSE_HORIZONTAL 718 | SPI.setBitOrder(MSBFIRST); // reset bitorder 719 | #endif 720 | } 721 | digitalWrite(CS, HIGH); 722 | } 723 | } 724 | //************************************************************************************************** 725 | void char2Arr(unsigned short ch, int PosX, short PosY) { //characters into arr 726 | int i, j, k, l, m, o1, o2, o3, o4; //in LEDarr 727 | PosX++; 728 | k = ch - 32; //ASCII position in font 729 | if ((k >= 0) && (k < 96)) //character found in font? 730 | { 731 | o4 = font1[k][0]; //character width 732 | o3 = 1 << (o4 - 2); 733 | for (i = 0; i < o4; i++) { 734 | if (((PosX - i <= maxPosX) && (PosX - i >= 0)) 735 | && ((PosY > -8) && (PosY < 8))) //within matrix? 736 | { 737 | o1 = helpArrPos[PosX - i]; 738 | o2 = helpArrMAX[PosX - i]; 739 | for (j = 0; j < 8; j++) { 740 | if (((PosY >= 0) && (PosY <= j)) || ((PosY < 0) && (j < PosY + 8))) //scroll vertical 741 | { 742 | l = font1[k][j + 1]; 743 | m = (l & (o3 >> i)); //e.g. o4=7 0zzzzz0, o4=4 0zz0 744 | if (m > 0) 745 | LEDarr[o2][j - PosY] = LEDarr[o2][j - PosY] | (o1); //set point 746 | else 747 | LEDarr[o2][j - PosY] = LEDarr[o2][j - PosY] & (~o1); //clear point 748 | } 749 | } 750 | } 751 | } 752 | } 753 | } 754 | 755 | //************************************************************************************************** 756 | void timer50ms() { 757 | static unsigned int cnt50ms = 0; 758 | static unsigned int cnt1s = 0; 759 | static unsigned int cnt1m = 0; 760 | static unsigned int cnt1h = 0; 761 | f_tckr50ms = true; 762 | cnt50ms++; 763 | if (cnt50ms == 20) { 764 | f_tckr1s = true; // 1 sec 765 | cnt1s++; 766 | cnt50ms = 0; 767 | } 768 | if (cnt1s == 60) { // 1h 769 | cnt1m++; 770 | cnt1s = 0; 771 | } 772 | if (cnt1m == 60) { // 1h 773 | cnt1h++; 774 | cnt1m = 0; 775 | } 776 | /* 777 | if (cnt1h == 24) { // 1d 778 | f_tckr24h = true; 779 | cnt1h = 0; 780 | } 781 | */ 782 | if (cnt1h == 1) { // // verify time (1 = every hour, 24 - every day) 783 | f_tckr24h = true; 784 | cnt1h = 0; 785 | } 786 | } 787 | //************************************************************************************************** 788 | // 789 | //The setup function is called once at startup of the sketch 790 | void setup() { 791 | // Add your initialization code here 792 | pinMode(CS, OUTPUT); 793 | digitalWrite(CS, HIGH); 794 | Serial.begin(115200); 795 | dht.begin(); 796 | temperatura = dht.readTemperature(); 797 | umiditate = dht.readHumidity(); 798 | Serial.print(temperatura); 799 | Serial.println("gr.Celsius"); 800 | //rtc.init(SDA, SCL); 801 | SPI.begin(); 802 | helpArr_init(); 803 | max7219_init(); 804 | max7219_set_brightness(0); 805 | rtc_init(SDA, SCL); 806 | clear_Display(); 807 | tckr.attach(0.05, timer50ms); // every 50 msec 808 | connect_to_WiFi(); 809 | tm* tt; 810 | tt = connectNTP(); 811 | if (tt != NULL) 812 | rtc_set(tt); 813 | else 814 | Serial.println("no timepacket received"); 815 | } 816 | //************************************************************************************************** 817 | // The loop function is called in an endless loop 818 | void loop() { 819 | //Add your repeated code here 820 | unsigned int sek1 = 0, sek2 = 0, min1 = 0, min2 = 0, std1 = 0, std2 = 0; 821 | unsigned int sek11 = 0, sek12 = 0, sek21 = 0, sek22 = 0; 822 | unsigned int min11 = 0, min12 = 0, min21 = 0, min22 = 0; 823 | unsigned int std11 = 0, std12 = 0, std21 = 0, std22 = 0; 824 | signed int x = 0; //x1,x2; 825 | signed int y = 0, y1 = 0, y2 = 0; 826 | bool updown = false; 827 | unsigned int sc1 = 0, sc2 = 0, sc3 = 0, sc4 = 0, sc5 = 0, sc6 = 0; 828 | bool f_scrollend_y = false; 829 | unsigned int f_scroll_x = false; 830 | 831 | z_PosX = maxPosX; 832 | d_PosX = -8; 833 | // x=0; x1=0; x2=0; 834 | 835 | refresh_display(); 836 | updown = true; 837 | if (updown == false) { 838 | y2 = -9; 839 | y1 = 8; 840 | } 841 | if (updown == true) { //scroll up to down 842 | y2 = 8; 843 | y1 = -8; 844 | } 845 | while (true) { 846 | yield(); 847 | if (f_tckr24h == true) { //syncronisize RTC every day 848 | f_tckr24h = false; 849 | tm* tt; 850 | tt = connectNTP(); 851 | if (tt != NULL) 852 | rtc_set(tt); 853 | else 854 | Serial.println("no timepacket received"); 855 | } 856 | if (f_tckr1s == true) // flag 1sek 857 | { 858 | rtc2mez(); 859 | sek1 = MEZ.sek1; 860 | sek2 = MEZ.sek2; 861 | min1 = MEZ.min1; 862 | min2 = MEZ.min2; 863 | std1 = MEZ.std1; 864 | std2 = MEZ.std2; 865 | y = y2; //scroll updown 866 | sc1 = 1; 867 | sek1++; 868 | if (sek1 == 10) { 869 | sc2 = 1; 870 | sek2++; 871 | sek1 = 0; 872 | } 873 | if (sek2 == 6) { 874 | min1++; 875 | sek2 = 0; 876 | sc3 = 1; 877 | } 878 | if (min1 == 10) { 879 | min2++; 880 | min1 = 0; 881 | sc4 = 1; 882 | } 883 | if (min2 == 6) { 884 | std1++; 885 | min2 = 0; 886 | sc5 = 1; 887 | } 888 | if (std1 == 10) { 889 | std2++; 890 | std1 = 0; 891 | sc6 = 1; 892 | } 893 | if ((std2 == 2) && (std1 == 4)) { 894 | std1 = 0; 895 | std2 = 0; 896 | sc6 = 1; 897 | } 898 | 899 | sek11 = sek12; 900 | sek12 = sek1; 901 | sek21 = sek22; 902 | sek22 = sek2; 903 | min11 = min12; 904 | min12 = min1; 905 | min21 = min22; 906 | min22 = min2; 907 | std11 = std12; 908 | std12 = std1; 909 | std21 = std22; 910 | std22 = std2; 911 | f_tckr1s = false; 912 | if (MEZ.sek12 == 35) 913 | f_scroll_x = true; 914 | 915 | if ((MEZ.std12 < 7) or (MEZ.std12 >19)) // change brighness for day or night 916 | { 917 | if (noapte == 0) 918 | { 919 | Serial.println("decrease brightness"); 920 | max7219_set_brightness(0); 921 | noapte = 1; 922 | } 923 | } 924 | else 925 | { 926 | if (noapte == 1) 927 | { 928 | Serial.print("increase brightness"); 929 | max7219_set_brightness(1); 930 | noapte = 0; 931 | } 932 | } 933 | if (MEZ.sek12 == 10) 934 | { 935 | if (WiFi.status() != WL_CONNECTED) { 936 | // delay(500); 937 | Serial.println("WiFi is NOT connected !"); 938 | } 939 | else 940 | Serial.println("WiFi is (re)connected !"); 941 | } 942 | if (MEZ.sek12 == 59) 943 | { 944 | temperatura = dht.readTemperature(); 945 | Serial.print("t = "); 946 | Serial.print(temperatura); 947 | Serial.print("gr.C h = "); 948 | umiditate = dht.readHumidity(); 949 | Serial.print(umiditate); 950 | Serial.println("%RH"); 951 | if (temperatura < 0) 952 | { 953 | temp = -10*temperatura; 954 | minus = 1; 955 | } 956 | else 957 | { 958 | minus = 0; 959 | temp = 10*temperatura; 960 | } 961 | tempz = temp/100; 962 | tempr = temp - 100*tempz; 963 | tempu = tempr/10; 964 | temps = tempr%10; 965 | } 966 | } // end 1s 967 | if (f_tckr50ms == true) { 968 | f_tckr50ms = false; 969 | if (f_scroll_x == true) { 970 | z_PosX++; 971 | d_PosX++; 972 | if (d_PosX == mult) 973 | z_PosX = 0; 974 | if (z_PosX == maxPosX) { 975 | f_scroll_x = false; 976 | d_PosX = -8; 977 | } 978 | } 979 | if (sc1 == 1) { 980 | if (updown == 1) 981 | y--; 982 | else 983 | y++; 984 | char2Arr(48 + sek12, z_PosX - 42, y); 985 | char2Arr(48 + sek11, z_PosX - 42, y + y1); 986 | if (y == 0) { 987 | sc1 = 0; 988 | f_scrollend_y = true; 989 | } 990 | } 991 | else 992 | char2Arr(48 + sek1, z_PosX - 42, 0); 993 | 994 | if (sc2 == 1) { 995 | char2Arr(48 + sek22, z_PosX - 36, y); 996 | char2Arr(48 + sek21, z_PosX - 36, y + y1); 997 | if (y == 0) 998 | sc2 = 0; 999 | } 1000 | else 1001 | char2Arr(48 + sek2, z_PosX - 36, 0); 1002 | 1003 | char2Arr(':', z_PosX - 32, 0); 1004 | 1005 | if (sc3 == 1) { 1006 | char2Arr(48 + min12, z_PosX - 25, y); 1007 | char2Arr(48 + min11, z_PosX - 25, y + y1); 1008 | if (y == 0) 1009 | sc3 = 0; 1010 | } 1011 | else 1012 | char2Arr(48 + min1, z_PosX - 25, 0); 1013 | 1014 | if (sc4 == 1) { 1015 | char2Arr(48 + min22, z_PosX - 19, y); 1016 | char2Arr(48 + min21, z_PosX - 19, y + y1); 1017 | if (y == 0) 1018 | sc4 = 0; 1019 | } 1020 | else 1021 | char2Arr(48 + min2, z_PosX - 19, 0); 1022 | 1023 | char2Arr(':', z_PosX - 15 + x, 0); 1024 | 1025 | if (sc5 == 1) { 1026 | char2Arr(48 + std12, z_PosX - 8, y); 1027 | char2Arr(48 + std11, z_PosX - 8, y + y1); 1028 | if (y == 0) 1029 | sc5 = 0; 1030 | } 1031 | else 1032 | char2Arr(48 + std1, z_PosX - 8, 0); 1033 | 1034 | if (sc6 == 1) { 1035 | char2Arr(48 + std22, z_PosX - 2, y); 1036 | char2Arr(48 + std21, z_PosX - 2, y + y1); 1037 | if (y == 0) 1038 | sc6 = 0; 1039 | } 1040 | else 1041 | char2Arr(48 + std2, z_PosX - 2, 0); 1042 | 1043 | char2Arr(' ', d_PosX+7, 0); 1044 | char2Arr(' ', d_PosX+1, 0); 1045 | char2Arr(' ', d_PosX-5, 0); 1046 | poz = 11; 1047 | char2Arr(WT_arr[MEZ.WT][0], d_PosX - poz, 0); //day of the week 1048 | poz = poz+6; 1049 | char2Arr(WT_arr[MEZ.WT][1], d_PosX - poz, 0); 1050 | poz = poz+6; 1051 | char2Arr(WT_arr[MEZ.WT][2], d_PosX - poz, 0); 1052 | poz = poz+6; 1053 | char2Arr(WT_arr[MEZ.WT][3], d_PosX - poz, 0); 1054 | poz = poz+6; 1055 | char2Arr(' ', d_PosX - poz, 0); 1056 | poz = poz+6; 1057 | char2Arr(48 + MEZ.tag2, d_PosX - poz, 0); //day 1058 | poz = poz+6; 1059 | char2Arr(48 + MEZ.tag1, d_PosX - poz, 0); 1060 | poz = poz+6; 1061 | char2Arr(' ', d_PosX - poz, 0); 1062 | char2Arr('.', d_PosX - poz, 0); 1063 | poz = poz+6; 1064 | 1065 | char2Arr(M_arr[MEZ.mon12 - 1][1], d_PosX - poz, 0); 1066 | poz = poz+6; 1067 | char2Arr(M_arr[MEZ.mon12 - 1][2], d_PosX - poz, 0); 1068 | poz = poz+6; 1069 | char2Arr(M_arr[MEZ.mon12 - 1][3], d_PosX - poz, 0); 1070 | poz = poz+6; 1071 | char2Arr(' ', d_PosX - poz, 0); 1072 | char2Arr('.', d_PosX - poz, 0); 1073 | poz = poz+6; 1074 | char2Arr('2', d_PosX - poz, 0); //year 1075 | poz = poz+6; 1076 | char2Arr('0', d_PosX - poz, 0); 1077 | poz = poz+6; 1078 | char2Arr(48 + MEZ.jahr2, d_PosX - poz, 0); 1079 | poz = poz+6; 1080 | char2Arr(48 + MEZ.jahr1, d_PosX - poz, 0); 1081 | poz = poz+6; 1082 | char2Arr(' ', d_PosX - poz, 0); 1083 | poz = poz+6; 1084 | char2Arr(' ', d_PosX - poz, 0); 1085 | poz = poz+6; 1086 | char2Arr(' ', d_PosX - poz, 0); 1087 | poz = poz+6; 1088 | 1089 | // my part (niq_ro part) 1090 | if (minus == 1) 1091 | char2Arr('-', d_PosX - poz, 0); 1092 | else 1093 | char2Arr('+', d_PosX - poz, 0); 1094 | poz = poz+6; 1095 | 1096 | if (tempz > 0) 1097 | { 1098 | char2Arr(48+tempz, d_PosX - poz, 0); 1099 | poz = poz+6; 1100 | } 1101 | char2Arr(48+tempu, d_PosX - poz, 0); 1102 | poz = poz+6; 1103 | 1104 | char2Arr(' ', d_PosX - poz, 0); 1105 | char2Arr('.', d_PosX - poz, 0); 1106 | poz = poz+6; 1107 | 1108 | char2Arr(48+temps, d_PosX - poz, 0); 1109 | poz = poz+6; 1110 | char2Arr('$', d_PosX - poz, 0); 1111 | poz = poz+6; 1112 | char2Arr('C', d_PosX - poz, 0); 1113 | poz = poz+6; 1114 | 1115 | char2Arr(' ', d_PosX - poz, 0); 1116 | poz = poz+6; 1117 | char2Arr(' ', d_PosX - poz, 0); 1118 | poz = poz+6; 1119 | 1120 | if (umiditate >= 10) 1121 | { 1122 | char2Arr(48 + (umiditate / 10), d_PosX - poz, 0); 1123 | poz = poz+6; 1124 | } 1125 | /* 1126 | char2Arr(48 + (umiditate % 10), d_PosX - poz, 0); 1127 | poz = poz+6; 1128 | char2Arr('%', d_PosX - poz, 0); 1129 | poz = poz+6; 1130 | char2Arr('R', d_PosX - poz, 0); 1131 | poz = poz+6; 1132 | char2Arr('H', d_PosX - poz, 0); 1133 | } 1134 | if (umiditate <= 9 && umiditate >0) 1135 | { 1136 | char2Arr(' ', d_PosX - poz, 0); 1137 | poz = poz+6; 1138 | */ 1139 | char2Arr(48 + (umiditate%10), d_PosX - poz, 0); 1140 | poz = poz+6; 1141 | char2Arr('%', d_PosX - poz, 0); 1142 | poz = poz+6; 1143 | char2Arr('R', d_PosX - poz, 0); 1144 | poz = poz+6; 1145 | char2Arr('H', d_PosX - poz, 0); 1146 | // } 1147 | poz = poz+6; 1148 | char2Arr(' ', d_PosX - poz, 0); 1149 | poz = poz+6; 1150 | char2Arr(' ', d_PosX - poz, 0); 1151 | poz = poz+6; 1152 | char2Arr(' ', d_PosX - poz, 0); 1153 | //poz = poz+6; 1154 | mult = poz + 5; 1155 | 1156 | // end Seby part 1157 | 1158 | refresh_display(); //alle 50ms 1159 | if (f_scrollend_y == true) { 1160 | f_scrollend_y = false; 1161 | } 1162 | } //end 50ms 1163 | if (y == 0) { 1164 | // do something else 1165 | } 1166 | } //end while(true) 1167 | //this section can not be reached 1168 | } 1169 | --------------------------------------------------------------------------------