Hallo,
ich hänge mich hier mal mit dran.
mit dem gezeigten Code habe ich mir was zusammengebastelt das mir an einem Pin ein 0-5V Signal erzeugt um einen Wechselrichter zu steuern.
Leider hab ich 0 Erfahrung mit Programmieren.
Ein Problem gild es noch in dem Code zu lösen , mal abgesehen vom Durcheinander:
Wenn keine Daten eindrudeln MUSS der Ausgang 0V haben, um zu verhindern das bei einem Fehler ggf. mit Voller LEistung eingespeist wird.
zusätzlich scheint der Code ztw zu hängen ??
evtl kann mir da jemand helfen?
byte inByte; //byte to store the serial buffer
byte smlMessage[1000];
const byte startSequence[] = { 0x1B, 0x1B, 0x1B, 0x1B, 0x01, 0x01, 0x01, 0x01 };//start sequence of SML protocol
const byte stopSequence[] = { 0x1B, 0x1B, 0x1B, 0x1B, 0x1A };//end sequence of SML protocol
const byte powerSequence[] = { 0x07, 0x01, 0x00, 0x10, 0x07, 0x00, 0xFF, 0x01, 0x01, 0x62, 0x1B, 0x52, 0x00, 0x55 }; //sequence preceeding the current "Wirkleistung" value (4 Bytes)
int smlIndex;//index counter within smlMessage array
int startIndex;//start index for start sequence search
int stopIndex;//start index for stop sequence search
int stage;//index to maneuver through cases
int currentpower; //variable to hold translated "Wirkleistung" value
int currentpower1;
byte analogpower; //Byte für analogen Ausgang
byte power[4]; //array that holds the extracted 4 byte "Wirkleistung" value
void setup() {
pinMode(9,OUTPUT);//setze PIN 9 für Output
Serial.begin(9600);
while (!Serial) {
; // wait for serial port to connect. Needed for native USB port only
}
}
void loop() {
switch (stage) {
case 0:
findStartSequence();
break;
case 1:
findStopSequence();
break;
case 2:
findPowerSequence(); //look for power sequence and extract
break;
case 3:
publishMessage();
break;
}
}
void findStartSequence() {
while (Serial.available())
{
inByte = Serial.read();//read serial buffer into array
if (inByte == startSequence[startIndex])//in case byte in array matches the start sequence at position 0,1,2...
{
smlMessage[startIndex] = inByte;//set smlMessage element at position 0,1,2 to inByte value
startIndex++;
if (startIndex == sizeof(startSequence))//all start sequence values have been identified
{
// Serial.println("Match found");
stage = 1;
smlIndex = startIndex;
startIndex = 0;
}
}
else {
startIndex = 0;
}
}
}
void findStopSequence() {
while (Serial.available())
{
inByte = Serial.read();
smlMessage[smlIndex] = inByte;
smlIndex++;
if (inByte == stopSequence[stopIndex])
{
stopIndex++;
if (stopIndex == sizeof(stopSequence))
{
stage = 2;
stopIndex = 0;
// after the stop sequence, ther are sill 3 bytes to come.
// One for the amount of fillbytes plus two bytes for calculating CRC.
for (int c = 0 ; c < 3 ; c++) {
smlMessage[smlIndex++] = Serial.read();
if (stopIndex == sizeof(stopSequence))
{
stage = 2;
stopIndex = 0;
// after the stop sequence passed, there are sill 3 bytes to come.
// One for the amount of fillbytes plus two bytes for calculating CRC.
delay(3); // wait for the 3 bytes to be received.
for (int c = 0 ; c < 3 ; c++) {
smlMessage[smlIndex++] = Serial.read();
}
// smlIndex is at this point one bigger than the amount of stored inBytes because it is incremented evreytime after reading.
// To store the real smlIndex, we have to substract the last incrementation.
smlIndex--;
}
}
}
}
else {
stopIndex = 0;
}
}
}
void findPowerSequence() {
byte temp; //temp variable to store loop search data
startIndex = 0; //start at position 0 of exctracted SML message
for(int x = 0; x < sizeof(smlMessage); x++){ //for as long there are element in the exctracted SML message
temp = smlMessage[x]; //set temp variable to 0,1,2 element in extracted SML message
if (temp == powerSequence[startIndex]) //compare with power sequence
{
startIndex++;
if (startIndex == sizeof(powerSequence)) //in complete sequence is found
{
for(int y = 0; y< 4; y++){ //read the next 4 bytes (the actual power value)
power[y] = smlMessage[x+y+1]; //store into power array
}
stage = 3; // go to stage 3
startIndex = 0;
}
}
else {
startIndex = 0;
}
}
currentpower = (power[0] << 24 | power[1] << 16 | power[2] << 8 | power[3]); //merge 4 bytes into single variable to calculate power value
}
void publishMessage() {
// int arrSize = 2 * smlIndex + 1;
// char smlMessageAsString[arrSize];
// char *myPtr = &smlMessageAsString[0]; //or just myPtr=charArr; but the former described it better.
//
// for (int i = 0; i < smlIndex; i++) {
// snprintf(myPtr, 3, "%02x", smlMessage[i]); //convert a byte to character string, and save 2 characters (+null) to charArr;
// myPtr += 2; //increment the pointer by two characters in charArr so that next time the null from the previous go is overwritten.
// }
//Serial.print("Byte count: ");
//Serial.println(smlIndex);
//Serial.print('\n');
//output 4 bytes of exctracted power bytes
//for(int x = 0; x < 4; x++){
//Serial.print(power[x],HEX);
//Serial.print(" ");
//}
//output calculated "Wirkleistung"
Serial.print("Leistung: ");
Serial.println(currentpower);
//hier wird aus currentpower dien Wert der nur zwischen 0 und 998
//sein kann , falls größer ist er immer 998
if(currentpower>998)currentpower=998;
//hier wird der int Currentpower in einen byte Wert gewandelt und durch 3,9 geteilt für das Verhältnis
//1000W = 100%, 255=100% entpricht 100/255=0,39 0,39*10 (10W entpricht 1% von 1000W)
byte analogpower = currentpower / 3.9;
Serial.println(analogpower);// gibt den analogwert aus zum Debug
analogWrite(9,analogpower);
int currentpower1 = currentpower;
Serial.print('\n');
//output 8 bytes of exctracted consumption bytes
for(int x = 0; x < 8; x++){
}
// clear the buffers
smlIndex = 0;
memset(smlMessage, 0, sizeof(smlMessage));
memset(power, 0, sizeof(power));
stage = 0; // start over
}