Thermocouples wrong values when external power supply

Post here about your Arduino projects, get help - for Adafruit customers!

Moderators: adafruit_support_bill, adafruit

Please be positive and constructive with your questions and comments.
Locked
User avatar
bdellal
 
Posts: 51
Joined: Tue Jun 10, 2014 6:00 pm

Thermocouples wrong values when external power supply

Post by bdellal »

Hi,
I have a weird problem. I am using an Arduino Mega and three of these thermocouples https://www.adafruit.com/product/269
They work perfectly when my Arduino is connected to the computer, but when I run it with a power supply( I tried 12V and 9V) the values are totally wrong. They show NAN or much too high or too low values changing every second. It happens when I use only the power supply and when I use the power supply and my laptop.

Here is my code, temperature measurement is in the TEMPERATURE sections. But I'm pretty sure it is a Hardware problem. It should be wired correctly because it works with my computer...

Code: Select all

//Pump durability tester code
//includes:
//-thermal shutdown circuit
//-motor speed control via relay
//-pump flowrate monitoring


// include the library code for I2C and the LCD shield:

#include "Adafruit_MAX31855.h"
#include <Wire.h>
#include <Adafruit_MCP23017.h>
#include <Adafruit_RGBLCDShield.h>

//DATALOGGING---------------------------------------------------------------------------
#include <SD.h>
#include "RTClib.h"

#define SYNC_INTERVAL 1000 // mills between calls to flush() - to write data to the card
uint32_t syncTime = 0; // time of last sync()

#define LOG_INTERVAL  1000 // mills between entries (reduce to take more/faster data)
RTC_DS1307 RTC; // define the Real Time Clock object

// for the data logging shield, we use digital pin 10 for the SD cs line
const int chipSelect = 10;

// the logging file
File logfile;

//DATALOGGING---------------------------------------------------------------------------

#define PIN_BUTTON                           52         // connects to the ON/OFF button

//#define PIN_I2C_1                          A4        // these pins provide serial communication with the LCD shield
//#define PIN_I2C_2                          A5        // these pins provide serial communication with the LCD shield

#define THRESHOLD_TEMPERATURE_Reservoir1        100        // maximum oil temperature for normal operation
#define THRESHOLD_TEMPERATURE_Reservoir2        100        // maximum oil temperature for normal operation
#define THRESHOLD_TEMPERATURE_AMBIENT            60        // maximum ambient temperature for normal operation

#define STATE_ESTOP_ACTIVE                 HIGH      // E-stop pin is pulled high internally, then grounded through E-stop button
                                                     // the button is NC, thus pressed means open means not grounded means HIGH
                                     

#define Relay_STOP                          44        // Relay control output 
#define Relay1                              46        // Relay speed1
#define Relay2                              48        // Relay speed2
#define Relay3                              50        // Relay speed3
#define thermoDO                            6         // Data out (shared)
#define thermoCS1                           3         // Chip select for thermocouple 1
#define thermoCLK                           5         // Clock (shared)
#define thermoCS2                           2         // Chip select for thermocouple 2
#define thermoCS3                           4         // Chip select for thermocouple 3
  
#define time                                double (millis()/1000)/60  // Program runtime.
// Variables will change:
long previousMillis = 0; 

// The shield uses the I2C SCL and SDA pins. On classic Arduinos
// this is Analog 4 and 5 so you can't use those for analogRead() anymore
// However, you can connect other I2C sensors to the I2C bus and share
// the I2C bus.

Adafruit_RGBLCDShield lcd = Adafruit_RGBLCDShield();
// this creates an LCD object that is controlled using the Adafruit library

Adafruit_MAX31855 thermocouple1(thermoCLK, thermoCS1, thermoDO);
Adafruit_MAX31855 thermocouple2(thermoCLK, thermoCS2, thermoDO);
Adafruit_MAX31855 thermocouple3(thermoCLK, thermoCS3, thermoDO);

//FLOWMETERS-------------------------------------------------------------------------------------


typedef struct Meter_t
{
  uint8_t pin;
  uint16_t pulses;
  uint8_t lastflowpinstate;
  uint32_t lastflowratetimer;
  float flowrate;
  float wert;
  float lmin;
};

volatile Meter_t meters[] = {                        // initialize meter array
                              { 28, 0, 0, 0, 0.0   }, // meter 1: pin, pulses, lastflowpinstate, lastflowratetimer, flowrate
                            //  { 30, 0, 0, 0, 0.0   },  // meter 2: pin, pulses, lastflowpinstate, lastflowratetimer, flowrate
                            //  { 32, 0, 0, 0, 0.0   },  // meter 3: pin, pulses, lastflowpinstate, lastflowratetimer, flowrate
                              { 34, 0, 0, 0, 0.0   },   // meter 4: pin, pulses, lastflowpinstate, lastflowratetimer, flowrate
                              { 36, 0, 0, 0, 0.0   }, // meter 5: pin, pulses, lastflowpinstate, lastflowratetimer, flowrate
                             // { 38, 0, 0, 0, 0.0   },  // meter 6: pin, pulses, lastflowpinstate, lastflowratetimer, flowrate
                              { 40, 0, 0, 0, 0.0   },  // meter 7: pin, pulses, lastflowpinstate, lastflowratetimer, flowrate
                              { 42, 0, 0, 0, 0.0   }   // meter 8: pin, pulses, lastflowpinstate, lastflowratetimer, flowrate
                                                     // add more meters as needed
                            };
#define NUM_METERS (sizeof(meters) / sizeof(Meter_t))

SIGNAL(TIMER0_COMPA_vect) {
  for (int m = 0; m < NUM_METERS; m++)
  {
    uint8_t x = digitalRead(meters[m].pin);

    if (x == meters[m].lastflowpinstate) {
      meters[m].lastflowratetimer++;
    }
    else
    {
      if (x == HIGH) {
        //low to high transition!
        meters[m].pulses++;
      }
      meters[m].lastflowpinstate = x;
      meters[m].flowrate = 1000.0;
      meters[m].flowrate /= meters[m].lastflowratetimer;  // in hertz
      meters[m].lastflowratetimer = 0;
    }
  }
}

void useInterrupt(boolean v) {
  if (v) {
    // Timer0 is already used for millis() - we'll just interrupt somewhere
    // in the middle and call the "Compare A" function above
    OCR0A = 0xAF;
    TIMSK0 |= _BV(OCIE0A);
  } 
  else {
    // do not call the interrupt function COMPA anymore
    TIMSK0 &= ~_BV(OCIE0A);
  }
  
  //FLOWMETERS-------------------------------------------------------------------------------------
}
  
void setup() {
  Serial.begin(9600);
  Serial.print("Flow sensor test!");
// declare the number of columns and rows for the LCD: 
lcd.begin(16, 2);

 //FLOWMETERS-------------------------------------------------------------------------------------

for (int m = 0; m < NUM_METERS; m++)
  {
    pinMode(meters[m].pin, INPUT);
    digitalWrite(meters[m].pin, HIGH);
    meters[m].lastflowpinstate = digitalRead(meters[m].pin);
  }

  useInterrupt(true);
  
   //FLOWMETERS-------------------------------------------------------------------------------------
  
//pinMode(PIN_ESTOP, INPUT_PULLUP);

pinMode(PIN_BUTTON, INPUT_PULLUP);
pinMode(Relay_STOP, OUTPUT);
digitalWrite(Relay_STOP, LOW);
lcd.setCursor(0,0);
lcd.print("Motor ON");
lcd.setCursor(0,1);
lcd.print("VFD Enabled");

 //SPEEDCONTROL-------------------------------------------------------------------------------------

  pinMode(Relay1, OUTPUT);
  digitalWrite(Relay1, HIGH);
  pinMode(Relay2, OUTPUT);
  digitalWrite(Relay2, HIGH);
  pinMode(Relay3, OUTPUT);
  digitalWrite(Relay3, HIGH);
  
   //SPEEDCONTROL-------------------------------------------------------------------------------------
   
   //DATALOGGING--------------------------------------------------------------------------------------
   
    // initialize the SD card
  Serial.print("Initializing SD card...");
  // make sure that the default chip select pin is set to
  // output, even if you don't use it:
  pinMode(10, OUTPUT);
  Serial.println("card initialized.");
  
   // create a new file
  char filename[] = "LOGGER00.CSV";
  for (uint8_t i = 0; i < 100; i++) {
    filename[6] = i/10 + '0';
    filename[7] = i%10 + '0';
    if (! SD.exists(filename)) {
      // only open a new file if it doesn't exist
      logfile = SD.open(filename, FILE_WRITE); 
      break;  // leave the loop!
    }
  }
  
  Serial.print("Logging to: ");
  Serial.println(filename);

  // connect to RTC
  Wire.begin();  
  
  logfile.println("millis,temperatureAmbient");
  
    //DATALOGGING--------------------------------------------------------------------------------------
  
} //end of setup()


void loop()
{

 //digitalWrite(Relay_STOP, LOW);  
 //checkBUTTON();
 //checkThermocouples();
 
 //TIMEKEEPING---------------------------------------------------------------------------------------
 
 unsigned long runtime = millis();  //runtime in millis
 int cycles = runtime/150000;        // calculate cycles
 runtime /= 1000;                   //runtime in seconds
 
 Serial.print("Runtime: ");  Serial.print(runtime); Serial.println(" seconds");
 Serial.print("Cycles: ");  Serial.println(cycles);
 Serial.println(" ");
 //TIMEKEEPING---------------------------------------------------------------------------------------
 
 
 
  //FLOWMETERS-------------------------------------------------------------------------------------
float lmin_max = 0.0;
float lmin_min = 1000.0;
int pump_max = 0;
int pump_min = 0;


 for (int m = 0; m < NUM_METERS; m++)
  {
    
  //average filter
  int i;
  meters[m].wert = 0;
  for(i = 0; i < 50; i++) {
  meters[m].wert += meters[m].flowrate;}
  meters[m].wert /= 50;
  
  meters[m].lmin = meters[m].wert;
  meters[m].lmin *=0.12;
  
  if( meters[m].lmin > lmin_max){
    lmin_max = meters[m].lmin;
    pump_max = m;
  }
  
  if (meters[m].lmin < lmin_min)
  {
    lmin_min = meters[m].lmin;
    pump_min = m;
  }

   // Serial.print("Min: "); Serial.print(lmin_min);Serial.print(" ");
   // Serial.print("Max: "); Serial.print(lmin_max);Serial.print(" ");
   //Serial.print("Diff: "); Serial.print(lmin_max - lmin_min);Serial.print(" ");
   // Serial.print("\n");

if ((lmin_max - lmin_min) >= 3.0)
{
  digitalWrite(Relay_STOP, HIGH);
     Serial.print(" ");
     Serial.print("Failed Pumps:");
     Serial.print(pump_min+1);
     Serial.print(" ");
     Serial.print(pump_max+1);
     Serial.print("Min: "); Serial.print(lmin_min);Serial.print(" ");
     Serial.print("Max: "); Serial.print(lmin_max);Serial.print(" ");
     unsigned long failtime = runtime;
     int failcycles = failtime/150000;
     Serial.print("Failed after Cycles:");
     Serial.print(cycles);
     
     lcd.setCursor(0,0);
     lcd.print("Failed Pump:");
     lcd.setCursor(1,0);
     lcd.print("Cycles:");
     lcd.print(failcycles);
     while(1)  {} 
}
  

    
    //lcd.print(flowrate);
    Serial.print("Meter ");
    Serial.print(m+1);
    Serial.print(" FLowrate in l/min: "); 
    Serial.println(meters[m].lmin);
    Serial.println("");
 //   Serial.print("Pulses: "); 
 //   Serial.println(meters[m].pulses, DEC);

    
    
  }
    //FLOWMETERS-------------------------------------------------------------------------------------
    
    //SPEEDCONTROL-------------------------------------------------------------------------------------
    
  unsigned long currentMillis = millis();  
 
  if(currentMillis - previousMillis < 120000) {
    digitalWrite(Relay1, LOW);
  }
  else {
    digitalWrite(Relay1, HIGH);
  }

  if(currentMillis - previousMillis > 120000 && currentMillis - previousMillis < 135000) {
    digitalWrite(Relay2, LOW);
 
  }
  
  else {
    digitalWrite(Relay2, HIGH);
  }

  if(currentMillis - previousMillis > 135000 && currentMillis - previousMillis < 150000) {
    digitalWrite(Relay3, LOW);
  }
  else {
    digitalWrite(Relay3, HIGH);
  }

  if(currentMillis - previousMillis >= 150000) {// reset the timer and start again
    previousMillis = currentMillis; 
  }
  
  //SPEEDCONTROL-------------------------------------------------------------------------------------
    
    
    
  //TEMPMONITORING-----------------------------------------------------------------------------------  
  double temperatureAmbient = thermocouple1.readCelsius();  // read motor temperature from thermocouple
  
  double temperatureReservoir1 = temperatureReservoir1 = thermocouple2.readCelsius();// read ambiant temperature from thermocouple

  double temperatureReservoir2 =  temperatureReservoir2 = thermocouple3.readCelsius();// read ambiant temperature from thermocouple

  
  Serial.print("Temperature Motor: ");
  Serial.print(temperatureAmbient); Serial.println(" C");
  
  Serial.print("Temperature Reservoir 1: ");
  Serial.print(temperatureReservoir1); Serial.println(" C");
  
  Serial.print("Temperature Reservoir 2: ");
  Serial.print(temperatureReservoir2); Serial.println(" C");
  Serial.println(" ");
  
  
 // lcd.setCursor(0,0);                                    // display data on LCD
 // lcd.print("Motor:    ");
 // lcd.print(temperatureAmbient);
 // lcd.print(" C");
 
 // lcd.setCursor(0,1);                                    // display data on LCD
 // lcd.print("Ambient:  ");
 // lcd.print(temperatureReservoir1);
 // lcd.print(" C");
  
  
  if (temperatureAmbient >= THRESHOLD_TEMPERATURE_AMBIENT)       // if temperature is too high
     {     
     digitalWrite(Relay_STOP, HIGH);                           // shut down Motor
     
//     lcd.setBacklight(RED);                                  // display warning on LCD
     lcd.clear();
     lcd.setCursor(0,0);
     lcd.print("T_Motor Limit Reached");
//     lcd.setCursor(0,1);
//     lcd.print("RT: ");
//     lcd.println(time);
//     lcd.println( " (min)");
     while(1)  {}                                            // wait for reset
   }
     
   if (temperatureReservoir1 > THRESHOLD_TEMPERATURE_Reservoir1)   // if temperature is too high
   {
     digitalWrite(Relay_STOP, HIGH);                           // shut down Motor
     
//     lcd.setBacklight(RED);                                  // display warning on LCD
     lcd.clear();
     lcd.setCursor(0,0);
     lcd.print("T_RES1 Limit Reached");
//     lcd.setCursor(0,1);
//     lcd.print("RT: ");
//     lcd.println(time);
//     lcd.println( " (min)");
     while(1)  {}                                            // wait for reset
   }
   if (temperatureReservoir2 > THRESHOLD_TEMPERATURE_Reservoir2)   // if temperature is too high
   {
     digitalWrite(Relay_STOP, HIGH);                           // shut down Motor
     
//     lcd.setBacklight(RED);                                  // display warning on LCD
     lcd.clear();
     lcd.setCursor(0,0);
     lcd.print("T_RES2 Limit Reached");
//     lcd.setCursor(0,1);
//     lcd.print("RT: ");
//     lcd.println(time);
//     lcd.println( " (min)");
     while(1)  {}                                            // wait for reset
   }

//TEMPMONITORING-----------------------------------------------------------------------------------

//PROGRAM RUNTIME---------------------------------------------------------------------------------------

if( cycles > 100000){
   digitalWrite(Relay_STOP, HIGH); 
   while(1)  {}                                            // wait for reset
   }

//PROGRAM RUNTIME---------------------------------------------------------------------------------------

 //DATALOGGING--------------------------------------------------------------------------------------
 DateTime now;
 
 // log milliseconds since starting
  uint32_t m = millis();
  logfile.print(m);           // milliseconds since start
  logfile.print(", "); 

 // fetch the time
  now = RTC.now();
  // log time
  logfile.print(now.unixtime()); // seconds since 1/1/1970
  logfile.print(", ");
  logfile.print('"');
  logfile.print(now.year(), DEC);
  logfile.print("/");
  logfile.print(now.month(), DEC);
  logfile.print("/");
  logfile.print(now.day(), DEC);
  logfile.print(" ");
  logfile.print(now.hour(), DEC);
  logfile.print(":");
  logfile.print(now.minute(), DEC);
  logfile.print(":");
  logfile.print(now.second(), DEC);
  logfile.print('"');

  logfile.print(", ");    
  logfile.print(temperatureAmbient); 
  
  //DATALOGGING--------------------------------------------------------------------------------------

}  // end of loop()


  







User avatar
adafruit_support_bill
 
Posts: 88087
Joined: Sat Feb 07, 2009 10:11 am

Re: Thermocouples wrong values when external power supply

Post by adafruit_support_bill »

Sounds like noise or possibly a grounding problem. Please post some photos showing your setup & all connections.

User avatar
bdellal
 
Posts: 51
Joined: Tue Jun 10, 2014 6:00 pm

Re: Thermocouples wrong values when external power supply

Post by bdellal »

Image

Image

It's hard to see, but it's already hardwired. All sensors share the same ground. It is connected to the arduino GND and is not used by anything else. They share 3.3V power too.

User avatar
adafruit_support_bill
 
Posts: 88087
Joined: Sat Feb 07, 2009 10:11 am

Re: Thermocouples wrong values when external power supply

Post by adafruit_support_bill »

The photos don't show where all those wires go. Form the looks of it, you do not have any power to the VIN pins on the boards. Are you trying to power them via the 3Vo pins?

User avatar
bdellal
 
Posts: 51
Joined: Tue Jun 10, 2014 6:00 pm

Re: Thermocouples wrong values when external power supply

Post by bdellal »

Yes I power them with 3V over the 3VO Pins. I tried to power one of them over the VIN with 5 V but now I have completely wrong results and still nan readings.

User avatar
adafruit_support_bill
 
Posts: 88087
Joined: Sat Feb 07, 2009 10:11 am

Re: Thermocouples wrong values when external power supply

Post by adafruit_support_bill »

We still can't see where all those wires go. What else is connected to the breadboard? What other components are sharing that ground? Where are the motors mentioned in the code?

User avatar
bdellal
 
Posts: 51
Joined: Tue Jun 10, 2014 6:00 pm

Re: Thermocouples wrong values when external power supply

Post by bdellal »

It is currently really confusing because I stopped hardwiring it when I saw the noise problems.
The power and the ground for the thermocouples come from a seperate pin and are only used by them. On the breadboard the lower power rows are connected to the arduino and give power to the eight flow meters and the relays. The ONE motor is not connected to the arduino. It is controlled by a VFD which is controlled by the relays shown. Like I said the three white cables from the thermocouples are the CS, the green and yellow wire are CLK and DO which are shared.

Image

Image

User avatar
bdellal
 
Posts: 51
Joined: Tue Jun 10, 2014 6:00 pm

Re: Thermocouples wrong values when external power supply

Post by bdellal »

Oh and I resoldered my 3V power connection to the thermocouples on the backside of the board.

User avatar
adafruit_support_bill
 
Posts: 88087
Joined: Sat Feb 07, 2009 10:11 am

Re: Thermocouples wrong values when external power supply

Post by adafruit_support_bill »

What is on the power bus that is running under the thermocouple amps?

With this type of problem, the best approach is often to simplify the configuration. Disconnect everything except for one thermocouple. Then start re-connecting things one-by-one until you see the problem again.

Locked
Please be positive and constructive with your questions and comments.

Return to “Arduino”