This time as first entry on the blog I want to share this useful project to log data reads from Zelio Logic (the well known base PLC).
Ok...let's talk about the Hardware:
In this case is the Zelio Logic SR3B261BD (24Vdc power supply, 16 24Vdc logic inputs, 10 relay outputs) but let's say that all Zelio Logics have the same programming port specs.
Well here is this puppy from inside:
The 6-way programming connector provides VCC, GND, TTL level serial RX and TX, and I2C SDA and SCL. The serial port is used by Zelio Soft to program the equipment. So basically it connects to and MCU (Arduino based) via Serial Port (+5V). Here's the pins used:
1 - VCC / 2 - GND / 3 - RX(serial in) / 5 - TX (serial out). Note:The pinout diagram is a front view as in the picture.
On the other side I make this Arduino UNO based Datalogger (ATMEGA328p) on his Version 1 (some upgrades to come as reverse polarity protection, etc..) here goes the schematics
This board is fully based on Adafruit datalogger (it can also be used in the same way) and adds some RS485 (not used in this case) and RTC (real time clock) not used as well becasue the Zelio Logic itself contains it's own RTC and is part of the data we are going to log...
Let's talk about the Software:
Here we are using one programming block on the Zelio logic known as Serial Out...this is the description on the Zelio Soft help:
The Serial Port Output function block is used to
send data stored in fixed addresses in the smart relay to other equipment via a
serial link
and this is the block program:
a quick description....every second (timer Li on pulse mode) sends a memorization pulse to the archive block, this archive block outputs the minute, hour, day, month, year and 2 archives on 16-bit format....all this in serial mode (115200, SERIAL_7E1. Arduino serial configuration)...also we have another block that takes inputs (16 input ) and outputs as a 16 bit word that is connected to the first word data on the serial output...in this way we have the state of the inputs to be logged...so summarizing the Zelio send this Data, time an date over serial port in response to some stream data query send to him (if you're interested send me a message or leave a comment for useful docs about the zelio protocol or Arduino sketch or whatever you need).
and finally the Arduino testing sketch (only for testing):
#include <SD.h>
const int chipSelect = 10;
const int redLED = 4;
const int greenLED = 5;
char charBuff[50];
int i = 0;
int j = 0;
char statusIO = 0;
byte valLow = 0;
byte valHigh = 0;
word value[16];
char filename[] = "LOGGER00.CSV";
// the logging file
File logfile;
void setup() {
Serial.begin(115200, SERIAL_7E1);
pinMode(redLED, OUTPUT);
pinMode(greenLED, OUTPUT);
pinMode(chipSelect, OUTPUT);
digitalWrite(redLED, LOW);
digitalWrite(greenLED, LOW);
if (!SD.begin(chipSelect)) {
return; // don't do anything more:
}
logfile = SD.open("LOGGER00.CSV", FILE_WRITE);
if (logfile) {
logfile.println("Data,Hora,Fecha,Archivo1,Archivo2");
logfile.close();
}
}
void loop() {
i = 0;
Serial.println(":01030000FF1810D6");
while(Serial.available() > 0){
charBuff[i] = Serial.read();
i++;
}
for(j=7; j<=(i-5); j++){
charBuff[j-7] = charBuff[j];
}
for(i=0;i<32;i++){
if(isDigit(charBuff[i]))
charBuff[i] = charBuff[i] - 48;
if(isAlpha(charBuff[i])){
switch(charBuff[i]){
case 'A': //65DEC
charBuff[i] = 0x0a;
break;
case 'B': //66DEC
charBuff[i] = 0x0b;
break;
case 'C':
charBuff[i] = 0x0c;
break;
case 'D':
charBuff[i] = 0x0d;
break;
case 'E':
charBuff[i] = 0x0e;
break;
case 'F':
charBuff[i] = 0x0f;
break;
}
}
}
j = 0;
for(i=0;i<8;i++){
valHigh = (charBuff[j] << 4) | charBuff[j+1];
valLow = (charBuff[j+2] << 4) | charBuff[j+3];
value[i] = word(valHigh, valLow);
j= j+4;
}
logfile = SD.open("LOGGER00.CSV", FILE_WRITE);
if (logfile) {
logfile.print(value[0], DEC);
logfile.print(", ");
logfile.print(value[2], DEC);
logfile.print(":");
logfile.print(value[1], DEC);
logfile.print(", ");
logfile.print(value[3], DEC);
logfile.print("/");
logfile.print(value[4], DEC);
logfile.print("/");
logfile.print(value[5], DEC);
logfile.print(", ");
logfile.print(value[6], DEC);
logfile.print(",");
logfile.print(value[7], DEC);
logfile.println(",");
logfile.close();
digitalWrite(greenLED, HIGH);
delay(500);
digitalWrite(greenLED, LOW);
}
else {
digitalWrite(redLED, HIGH);
delay(500);
digitalWrite(redLED, LOW);
}
logfile.flush();
delay(3000);
}
and voila...we have an excel .CSV file with headers and the data formatted from the Zelio logic....
I hope this is useful for you and all questions and comments are welcome....see you next time.