Está en la página 1de 10

#include <DallasTemperature.

h>
#include <OneWire.h>

//temporizador calentadores
const int inputPin = 7; // pin digital para la señal de entrada
const int outputPin = 8; // pin digital para el relé
unsigned long startTime = 0; // tiempo de inicio del temporizador
bool timerActive = false; // indicador de si el temporizador está activo o no
bool lastInputState = LOW; // estado anterior de la señal de entrada
unsigned int digitalPins = 0;
/// Define variables to track scan times
unsigned long Time;
byte LastBroadcast;
// Define variables for reading IO
bool LBLr; // Left Blinker from Digital in on Arduino
bool RBLr; // Right Blinker from Digital in on Arduino
bool HBr; // High Beams from Digital in on Arduino
bool MALFr; // Check Engine Light from Digital in on Arduino

// Defin pin modes for physical IO


int LBLPin = 43; //Left Blinker on Pin 43
int RBLPin = 45; // Right Blinker on Pin 45
int HBPin = 47; // High Beams on Pin 47
int MALFPin = 49; // Check Engine (MALF) on Pin 49

int analogPins[7] = {0};

volatile int rpm = 0;


unsigned int kpa = 992; // 99.2
unsigned int tps = 965; // 96.5
unsigned int clt = 80; // 80 - 100
unsigned int textCounter = 0;

//Sensor temperatura
OneWire ourWire(2);
DallasTemperature sensor1(&ourWire);

// incoming data
byte incomingFrame[17] = { 0 };
unsigned int incomingFramePos = 0;

void setup()
{
#if defined (READWRITE_PINS)
// set digital pins as outputs
for (int i=1; i<14; i++)
{
pinMode(i, OUTPUT);
}
#endif

// init serial
Serial.begin(115200);
//Sensor de temperatura
sensor1.begin();

//Temorizador calentadores
pinMode(inputPin, INPUT);
pinMode(outputPin, OUTPUT);

//Sensor de RPM
pinMode(3, INPUT);
attachInterrupt(0, interrupcion0, RISING);
delay(100);

Serial.begin(115200); //for diagnostics


Serial1.begin(115200); // for TTL to Dash

pinMode(LBLPin, INPUT_PULLUP); // Left Blinker will ground when activated


pinMode(RBLPin, INPUT_PULLUP); // Right Blinker will ground when activated
pinMode(HBPin, INPUT_PULLUP); // High Beams will ground when activated
pinMode(MALFPin, INPUT_PULLUP); //Check engine light will ground when activated
}

void loop()
{
// leer estado de la señal de entrada
int inputState = digitalRead(inputPin);

// si la señal de entrada está activa y el temporizador no está activo o el


estado acaba de cambiar, iniciarlo
if (inputState == HIGH && (!timerActive || lastInputState == LOW)) {
if (lastInputState == LOW) { // si el estado anterior de la señal de entrada era
LOW, reiniciar el temporizador
startTime = millis(); // guardar el tiempo de inicio
}
timerActive = true; // indicar que el temporizador está activo
}

// si el temporizador está activo y han pasado 10 segundos, desactivar el relé y


reiniciar el temporizador
if (timerActive && millis() - startTime >= 10000) {
digitalWrite(outputPin, LOW); // desactivar el relé
timerActive = false; // indicar que el temporizador ya no está activo
}

// si la señal de entrada acaba de cambiar de estado de alta a baja y el


temporizador está activo, desactivar el relé
if (inputState == LOW && lastInputState == HIGH && timerActive) {
digitalWrite(outputPin, LOW); // desactivar el relé
}

// guardar estado actual de la señal de entrada para comparar en la siguiente


iteración
lastInputState = inputState;

// si el temporizador está activo, activar el relé


if (timerActive) {
digitalWrite(outputPin, HIGH); // activar el relé
}
//Luces arduino
Time = millis();

// Go read the ardiuno IO


ReadIOPins();

// Send Data to CanBus every 23 millisecons


if (Time - LastBroadcast > 23) {
LastBroadcast = millis();
BuildCanFrames();
}
}

void ReadIOPins(){
LBLr = !digitalRead(LBLPin);
RBLr = !digitalRead(RBLPin);
HBr = !digitalRead(HBPin);
MALFr = !digitalRead(MALFPin);
}

void BuildCanFrames()
{
byte CanBuffer[8];

// build & send CAN frames to RealDash.


// a CAN frame payload is always 8 bytes containing data in a manner
// described by the RealDash custom channel description XML file
// all multibyte values are handled as little endian by default.
// endianess of the values can be specified in XML file if it is required to use
big endian values

// build 1st CAN frame:


CanBuffer[0] = HBr;
CanBuffer[1] = MALFr;
CanBuffer[2] = LBLr;
CanBuffer[3] = RBLr;
CanBuffer[4] = 0;
CanBuffer[5] = 0;
CanBuffer[6] = 0;
CanBuffer[7] = 0;

ReadDigitalStatuses();
ReadAnalogStatuses();
SendCANFramesToSerial();
ReadIncomingSerialData();
sensor1.requestTemperatures();
float temp= sensor1.getTempCByIndex(0);
Serial.print(rpm * 60);

{
rpm = 0;
}
if (kpa++ > 2500)
{
kpa = 10;
}
if (tps++ > 1000)
{
tps = 0;
}

{
clt = temp;
}

// simple counter for sending the text frame to avoid sending it too often.
if (textCounter++ > 4000)
{
textCounter = 0;
}

delay(5);
}

void interrupcion0() // Funcion que se ejecuta durante cada interrupion


{
rpm++; // Se incrementa en uno el contador
}

void ReadDigitalStatuses()
{
#if defined (READWRITE_PINS)
// read status of digital pins (1-13)
digitalPins = 0;

int bitposition = 0;
for (int i=1; i<14; i++)
{
if (digitalRead(i) == HIGH) digitalPins |= (1 << bitposition);
bitposition++;
}
#endif
}

void ReadAnalogStatuses()
{
#if defined (READWRITE_PINS)
// read analog pins (0-7)
for (int i=0; i<7; i++)
{
analogPins[i] = analogRead(i);
}
#endif
}

void SendCANFramesToSerial()
{
byte frameData[8];

// build & send CAN frames to RealDash.


// a CAN frame payload is always 8 bytes containing data in a manner
// described by the RealDash custom channel description XML file
// all multibyte values are handled as little endian by default.
// endianess of the values can be specified in XML file if it is required to use
big endian values

// build 1st CAN frame, RPM, MAP, CLT, TPS (just example data)
memcpy(frameData, &rpm, 2);
memcpy(frameData + 2, &kpa, 2);
memcpy(frameData + 4, &clt, 2);
memcpy(frameData + 6, &tps, 2);

// write first CAN frame to serial


SendCANFrameToSerial(3200, CanBuffer);

// build 2nd CAN frame, Arduino digital pins and 2 analog values
memcpy(frameData, &digitalPins, 2);
memcpy(frameData + 2, &analogPins[0], 2);
memcpy(frameData + 4, &analogPins[1], 2);
memcpy(frameData + 6, &analogPins[2], 2);

// write 2nd CAN frame to serial


SendCANFrameToSerial(3201, frameData);

// build 3rd CAN frame, rest of Arduino analog values


memcpy(frameData, &analogPins[3], 2);
memcpy(frameData + 2, &analogPins[4], 2);
memcpy(frameData + 4, &analogPins[5], 2);
memcpy(frameData + 6, &analogPins[6], 2);

// write 3rd CAN frame to serial


SendCANFrameToSerial(3202, frameData);

// build 4th frame, this is a text extension frame


// only send once at 1000 loops
if (textCounter == 0)
{
SendTextExtensionFrameToSerial(3203, "");
}
else if (textCounter == 1000)
{
SendTextExtensionFrameToSerial(3203, "Tomorrow's forecast: Lots of sun and 30
degrees centigate");
}
else if (textCounter == 2000)
{
SendTextExtensionFrameToSerial(3203, "Now Playing: Insert your favorite song
info here");
}
else if (textCounter == 3000)
{
SendTextExtensionFrameToSerial(3203, "Message from Arduino: All systems running
at nominal efficiency");
}
}

void SendCANFrameToSerial(unsigned long canFrameId, const byte* frameData)


{
// the 4 byte identifier at the beginning of each CAN frame
// this is required for RealDash to 'catch-up' on ongoing stream of CAN frames
const byte serialBlockTag[4] = { 0x44, 0x33, 0x22, 0x11 };
Serial1.write(serialBlockTag, 4);

// the CAN frame id number (as 32bit little endian value)


Serial1.write((const byte*)&canFrameId, 4);

// CAN frame payload


Serial1.write(frameData, 8);
}

void SendTextExtensionFrameToSerial(unsigned long canFrameId, const char* text)


{
if (text)
{
// the 4 byte identifier at the beginning of each CAN frame
// this is required for RealDash to 'catch-up' on ongoing stream of CAN frames
const byte textExtensionBlockTag[4] = { 0x55, 0x33, 0x22, 0x11 };
Serial.write(textExtensionBlockTag, 4);

// the CAN frame id number (as 32bit little endian value)


Serial.write((const byte*)&canFrameId, 4);

// text payload
Serial.write(text, strlen(text) + 1);
}
}

void ReadIncomingSerialData()
{
while (Serial.available() > 0)
{
// little bit of extra effort here, since especially Bluetooth connections
// may leave unsent/received data in internal buffer for a long time
// therefore, we cannot be sure that incoming byte stream really starts at
// where we expect it to start.

// read one byte from serial stream


incomingFrame[incomingFramePos++] = Serial.read();

// check the first incoming bytes tag (0x44, 0x33, 0x22, 0x11)
if (incomingFrame[0] != 0x44)
{
// first incoming byte is not 0x44,
// the tag at the beginning of the frame does not match, this is an invalid
frame
// just zero the incomingFrame buffer and start expecting first byte again
memset(incomingFrame, 0, 17);
incomingFramePos = 0;
}

if (incomingFramePos >= 17)


{
// frame complete, process it
ProcessIncomingFrame(incomingFrame);

// zero the incomingFrame buffer and start expecting first byte again
memset(incomingFrame, 0, 17);
incomingFramePos = 0;
}
}
}

void ProcessIncomingFrame(const byte* frame)


{
// first four bytes contain set value frame separator bytes, always
0x44,0x33,0x22,x11
// check that first 4 bytes match the tag
if (frame[0] != 0x44 ||
frame[1] != 0x33 ||
frame[2] != 0x22 ||
frame[3] != 0x11)
{
// frame tag does not match, wait for another frame
return;
}

// next four bytes contain set value CAN frame id in little endian form
unsigned long canFrameId = 0;
memcpy(&canFrameId, frame + 4, 4);

// next 8 bytes are the frame data


// ...

// last byte is check byte calculated as sum of previous 13 bytes (ignore


overflow)
byte checkByte = 0;
for (int i=0; i<16; i++)
{
checkByte += frame[i];
}

if (frame[16] == checkByte)
{
// checksum match, this is a valid set value-frame:
// the frame payload data is in frame + 8 bytes
HandleIncomingSetValueFrame(canFrameId, frame + 8);
}
}

void HandleIncomingSetValueFrame(unsigned long canFrameId, const byte* frameData)


{
if (canFrameId == 3201)
{
memcpy(&digitalPins, frameData, 2);
memcpy(&analogPins[0], frameData + 2, 2);
memcpy(&analogPins[1], frameData + 4, 2);
memcpy(&analogPins[2], frameData + 6, 2);

#if defined (READWRITE_PINS)


// write digital pins
for (int i=0; i<13; i++)
{
digitalWrite(i + 1, (digitalPins & (1 << i)) ? HIGH : LOW);
}

analogWrite(0, analogPins[0]);
analogWrite(1, analogPins[1]);
analogWrite(2, analogPins[2]);
#endif
}
else if (canFrameId == 3202)
{
memcpy(&analogPins[3], frameData + 0, 2);
memcpy(&analogPins[4], frameData + 2, 2);
memcpy(&analogPins[5], frameData + 4, 2);
memcpy(&analogPins[6], frameData + 6, 2);

#if defined (READWRITE_PINS)


analogWrite(3, analogPins[3]);
analogWrite(4, analogPins[4]);
analogWrite(5, analogPins[5]);
analogWrite(6, analogPins[6]);
#endif
}
}

// =======================================================
// Sample Program for sending digital singals to RealDash
// =======================================================

/// Define variables to track scan times


unsigned long Time;
byte LastBroadcast;

// Define variables for reading IO


bool LBLr; // Left Blinker from Digital in on Arduino
bool RBLr; // Right Blinker from Digital in on Arduino
bool HBr; // High Beams from Digital in on Arduino
bool MALFr; // Check Engine Light from Digital in on Arduino

// Defin pin modes for physical IO


int LBLPin = 43; //Left Blinker on Pin 43
int RBLPin = 45; // Right Blinker on Pin 45
int HBPin = 47; // High Beams on Pin 47
int MALFPin = 49; // Check Engine (MALF) on Pin 49

void setup() {
Serial.begin(115200); //for diagnostics
Serial1.begin(115200); // for TTL to Dash

pinMode(LBLPin, INPUT_PULLUP); // Left Blinker will ground when activated


pinMode(RBLPin, INPUT_PULLUP); // Right Blinker will ground when activated
pinMode(HBPin, INPUT_PULLUP); // High Beams will ground when activated
pinMode(MALFPin, INPUT_PULLUP); //Check engine light will ground when activated

}
// =======================================================
void loop() {

Time = millis();

// Go read the ardiuno IO


ReadIOPins();

// Send Data to CanBus every 23 millisecons


if (Time - LastBroadcast > 23) {
LastBroadcast = millis();
BuildCanFrames();
}
}

void ReadIOPins(){
LBLr = !digitalRead(LBLPin);
RBLr = !digitalRead(RBLPin);
HBr = !digitalRead(HBPin);
MALFr = !digitalRead(MALFPin);
}

void BuildCanFrames()
{
byte CanBuffer[8];

// build & send CAN frames to RealDash.


// a CAN frame payload is always 8 bytes containing data in a manner
// described by the RealDash custom channel description XML file
// all multibyte values are handled as little endian by default.
// endianess of the values can be specified in XML file if it is required to use
big endian values

// build 1st CAN frame:


CanBuffer[0] = HBr;
CanBuffer[1] = MALFr;
CanBuffer[2] = LBLr;
CanBuffer[3] = RBLr;
CanBuffer[4] = 0;
CanBuffer[5] = 0;
CanBuffer[6] = 0;
CanBuffer[7] = 0;

// write first CAN frame to serial


SendCANFrameToSerial(3200, CanBuffer);
}

void SendCANFrameToSerial(unsigned long canFrameId, const byte* frameData)


{
// the 4 byte identifier at the beginning of each CAN frame
// this is required for RealDash to 'catch-up' on ongoing stream of CAN frames
const byte serialBlockTag[4] = { 0x44, 0x33, 0x22, 0x11 };
Serial1.write(serialBlockTag, 4);

// the CAN frame id number (as 32bit little endian value)


Serial1.write((const byte*)&canFrameId, 4);

// CAN frame payload


Serial1.write(frameData, 8);
}

También podría gustarte