Go Down

Topic: Scrittura codice per impianto birra cerco collaboratori Monza/Milano (Read 8 times) previous topic - next topic

niki77



basta che alla fine dellì'operazione aggiungi '- 3.0' e sei a posto.

Ciao!


Pensi veramente che sottraendo 3 gradi così a muzzo  si risolva il problema??
Vi è una spiegazione scientifica a tutto.
La fede è solo quell'anello che si porta al dito dopo il matrimonio.

lesto

se vuoi fae le cose fatte bene, prendo un cubetto di ghiaccio e fai la misura, (0°), poi prendi una trazza di acqua calda e fai la prova (confronto col mercurio), poi una misura a temperatura ambiente sempre a confronto con il termometro a mercurio.

se in tutti i casi l'errore è 3gradi, allora sì, è così semplice. Altrimenti devi trovare la curva (o la retta) che unisce i punti trovati, e poi il valore che leggerai lo metterai nella funzione curva/retta e otterrai come risultato la temperatura vera.
sei nuovo? non sai da dove partire? leggi qui: http://playground.arduino.cc/Italiano/Newbie

niki77

La dalla DS18b20  è una sonda di precisione che restituisce direttamente il valore in gradi celsius.

Tratto dal datasheets , pagina 3 di 22:

The DS18B20 output temperature data is calibrated in degrees  Celsius.

Per esperienza mia, sono tutte abbastanza precise ed uno scostamento di 3 gradi è inammissibile.
Secondo me il test fornito da MrLofraz è inattendibile.

@Lesto: ritengo che sia impossibile che in tutto il range misurabile ci possa essere uno scostamento costante di 3 gradi.

Prova ad utilizzare la libreria presente  a questo indirizzo con relativo esempio  , è sicuramente più completa : DallasTemperature library

Poi se non ricordo male la sonda che hai tu è quella rivestita di plastica, potrebbe essere quello il problema , un cattivo trasferimento termico tra l'involucro e il sensore potrebbe esserne la causa, ma se fosse questo non ha sicuramente un andamento lineare nel tempo.

Prova ad immergere entrambi i termometri in acqua fredda e a lasciarli li per un pò di tempo,il valore della tua sonda dovrebbe decrescere nel tempo fino a stabilizzarsi ad un valore comuque non corretto (più alto della T reale).

@MrLofraz: lascia perdere il parasite mode per ora, t'infogni di più e basta!


Vi è una spiegazione scientifica a tutto.
La fede è solo quell'anello che si porta al dito dopo il matrimonio.

gingardu

mah,...   un terrmometro ambientale  che sballa di 3 gradi  deve finire in posto solo 
la pattumiera
Le cose si possono considerare facili in due casi: quando le si conosce bene o quando non le si conosce affatto...

lesto


@Lesto: ritengo che sia impossibile che in tutto il range misurabile ci possa essere uno scostamento costante di 3 gradi.


anche io, ma magari è un "semplice" errore di calibrazione dalla fabbrica..
sei nuovo? non sai da dove partire? leggi qui: http://playground.arduino.cc/Italiano/Newbie

niki77

Come si può notare QUI gli scostamenti rilevati su un campione di 35 sonde (10 DS18s20 e 25 DS18b20) sono irrisori, o perlomeno molto al di sotto di quanto ci serve.
Vi è una spiegazione scientifica a tutto.
La fede è solo quell'anello che si porta al dito dopo il matrimonio.

PaoloP

Alla fine le librerie ti servono tutte e due.
Sia quella indicata da Nik77 --> http://download.milesburton.com/Arduino/MaximTemperature/DallasTemperature_372Beta.zip
Che quella di llluca --> http://www.pjrc.com/teensy/arduino_libraries/OneWire.zip
Infatti la libreria di Miles si appoggia alla OneWire (sempre di Miles).

Il codice di esempio (preso sempre dalla wiki di Miles) è:
Code: [Select]
#include <OneWire.h>
#include <DallasTemperature.h>

// Data wire is plugged into port 2 on the Arduino
#define ONE_WIRE_BUS 2

// Setup a oneWire instance to communicate with any OneWire devices (not just Maxim/Dallas temperature ICs)
OneWire oneWire(ONE_WIRE_BUS);

// Pass our oneWire reference to Dallas Temperature.
DallasTemperature sensors(&oneWire);

void setup(void)
{
  // start serial port
  Serial.begin(9600);
  Serial.println("Dallas Temperature IC Control Library Demo");

  // Start up the library
  sensors.begin();
}

void loop(void)
{
  // call sensors.requestTemperatures() to issue a global temperature
  // request to all devices on the bus
  Serial.print("Requesting temperatures...");
  sensors.requestTemperatures(); // Send the command to get temperatures
  Serial.println("DONE");
 
  Serial.print("Temperature for the device 1 (index 0) is: ");
  Serial.println(sensors.getTempCByIndex(0)); 
}


Per il collegamento ricordati la resistenza di pull-up sul pin centrale.



llluca


terrmometro ambientale  che sballa di 3 gradi 


secondo me l' errore dovrebbe trovarsi:
Code: [Select]
if (type_s) {
    raw = raw << 3; // 9 bit resolution default
    if (data[7] == 0x10) {
      // count remain gives full 12 bit resolution
      raw = (raw & 0xFFF0) + 12 - data[6];
    }

tuxduino


Scusate, eh, cosa centra sto PID?
non basta rilevare la temperatura con un sensorino e accendere e spegnere il riscaldatore per mantenere la temperatura prefissata? :smiley-mr-green:


Ma infatti...

http://www.arduino.cc/playground/Main/BarebonesPIDForEspresso

altri interessanti risultati cercando "arduino pid temperatura".

flz47655

Ho letto solo l'ultima pagina della discussione ma lasciate perdere la vasca col ghiaccio non è facile realizzarla per tarare con precisione il termometro.
Ci sono diverse varianti e tanti fake cinesi del DS18b20 che hanno un'accuratezza minore.
In genere il problema è che ci vogliono molti minuti se c'è un metallo di mezzo per segnare la temperatura giusta, è come il termometro della febbre ma molto più lento, sopratutto se si usano dei fake comprati su ebay

Ciao

flz47655

Ragazzi ho visto il codice ma non è molto bello, non fate il check sul CRC dei dati, la libreria ha un bug per le temperature negative, dovete correggerlo se andate sotto zero, ecco il codice che ho utilizzato per il mio termometro, utilizza un display LCD ed ha funzionalità di risparmio energetico, non dovreste avere problemi ad estrapolare il codice di controllo e lettura del termometro. La libreria è http://www.pjrc.com/teensy/td_libs_OneWire.html

Ciao

Code: [Select]
// Termometer DS18B20
#include <LiquidCrystal.h>
#include <OneWire.h>

// WatchDog is used to save energy instead
#include <avr/power.h>
#include <avr/sleep.h>
#include <avr/wdt.h>

const byte lcd_rs = 7;
const byte lcd_e = 5;
const byte lcd_d4 = 4;
const byte lcd_d5 = 3;
const byte lcd_d6 = 2;
const byte lcd_d7 = 1;

LiquidCrystal lcd(lcd_rs, lcd_e, lcd_d4, lcd_d5, lcd_d6, lcd_d7);
OneWire  ds(9);

volatile boolean f_wdt=1;
// Watchdog Interrupt Service / is executed when  watchdog timed out
ISR(WDT_vect) {
f_wdt=1;  // set global flag
}
void setupWatchdog(byte wdp0, byte wdp1, byte wdp2, byte wdp3) {
  // WDTCSR - Watchdog timer Control Register, used for configuring the time-out, mode of operation, etc.
  // MCUSR - MCU Status Register, used to tell the cause of the last reset, such as brown-out reset, watchdog reset, etc.
  // NOTE: for security reasons, there is a timed sequence for clearing the WDE and changing the time-out configuration.
  // If you don't use this sequence properly, you'll get unexpected results.
  cli(); //disable global interrupts
  wdt_reset();
  MCUSR &= ~(1<<WDRF);  // Clear the reset flag 
  // In order to change WDE or the prescaler, we need to set WDCE (This will allow updates for 4 clock cycles)
  WDTCSR |= (1<<WDCE) | (1<<WDE);  // Set WD_ChangeEnable and WD_resetEnable to alter the register 
  WDTCSR = wdp0<<WDP0 | wdp1<<WDP1 | wdp2<<WDP2 | wdp3<<WDP3;    // set new watchdog timeout value   
  WDTCSR |= _BV(WDIE);  // Enable the WD interrupt (note no reset) 
  sei(); //enable global interrupts
}
void Sleep()
{
    set_sleep_mode(SLEEP_MODE_PWR_DOWN);
    // Set sleep enable (SE) bit:
    sleep_enable();
    // Put the device to sleep:
    sleep_mode(); // ZZZ....
    // Upon waking up, sketch continues from this point.
    sleep_disable();   
}
void sleep250ms()
{
    setupWatchdog(0,0,1,0);
    Sleep();
}
void sleep500ms()
{
    setupWatchdog(1,0,1,0);
    Sleep();
}
void sleepSecond()
{
    setupWatchdog(0,1,1,0);
    Sleep();
}
void setup() {
  // Stabilize voltage
  delay(5);
 
  // Disable ADC, SPI and TWI 
  power_adc_disable();  // Disable the Analog to Digital Converter module.
  power_spi_disable();  // Disable the Serial Peripheral Interface module.
  power_twi_disable();  // Disable the Two Wire Interface module.
  power_usart0_disable();  // Disable the USART 0 module. 
   
  lcd.begin(16, 2);
  lcd.clear();
 
  lcd.print("Thermometer v1"); 
  sleepSecond(); 
  lcd.clear();
}

byte deviceFounds = 0;
void loop() {
  if (f_wdt==1) // wait for timed out watchdog
    f_wdt=0;   

  byte data[12];
  byte addr[8];
  float celsius;
 
  // Search for the next device. The addrArray is an 8 byte array. If a device is found, addrArray is filled with the device's address and true is returned.
  // If no more devices are found, false is returned.
  if (!ds.search(addr)) {
    if(deviceFounds == 0)
    {
      lcd.clear();
      lcd.setCursor(0, 0); 
      lcd.print("No devices found"); // No more addresses     
      lcd.setCursor(0, 1);
      lcd.print("Try check probe"); // No more addresses     
      sleepSecond();
    }
    deviceFounds = 0;
   
    // Begin a new search. The next use of search will begin at the first device.
    ds.reset_search();
    sleep250ms();
    return;
  }else{
   deviceFounds++;
  }
 
  // Compute a CRC check on an array of data.
  if (OneWire::crc8(addr, 7) != addr[7]) {   
      lcd.clear();
      lcd.setCursor(0, 0);                 
      lcd.print("Address Error");     
      lcd.setCursor(0, 1);
      lcd.print("CRC is not valid");
      sleepSecond();
      return;
  }   

  // Reset the 1-wire bus. Usually this is needed before communicating with any device.
  ds.reset();
  // Select a device based on its address. After a reset, this is needed to choose which device you will use,
  // and then all communication will be with that device, until another reset.
  ds.select(addr); 
  // Write a byte, and leave power applied to the 1 wire bus.
  ds.write(0x44);         // start conversion, with parasite power on at the end
   
  // from Datasheet max conversion time is 750ms
  sleep500ms();
  sleep250ms();
 
  ds.reset(); 
  ds.select(addr);   
  ds.write(0xBE);         // Read Scratchpad
    for (byte i = 0; i < 9; i++) {  // we need 9 bytes
    data[i] = ds.read();
  }

  // Check data with CRC
  if (OneWire::crc8(data, 8) != data[8]) {   
      lcd.clear();
      lcd.setCursor(0, 0);                 
      lcd.print("Data Error");     
      lcd.setCursor(0, 1);
      lcd.print("CRC is not valid");
      sleepSecond();
      return;
  }
 
  // convert the data to actual temperature
  int raw = (data[1] << 8) | data[0];
  byte cfg = (data[4] & 0x60); // default is 12 bit resolution, 750 ms conversion time
 
  celsius = (float)raw / 16.0;

  lcd.clear();
  lcd.setCursor(0, 0);
  lcd.print("Temperatura");
  /*
  for( i = 0; i < 8; i++) {   
    lcd.print(addr[i], HEX);
  }  */
  lcd.setCursor(0, 1);
  lcd.print(celsius);
  lcd.print("C");
}

MrLofraz

Mi sono arenato, non riesco ad andare avanti.
La temperatura è sempre "fuori" di tre gradi, sono andato completamente in palla!

flz47655

Se è fuori di 3 gradi fissa allora tanto vale correggerla via sw.. dove hai preso il sensore?

MrLofraz

Da robot italy. Oggi però, l'ho riprovata e mi sembrava meglio. Ho caricato un'altra libreria per il sensore. Adesso volevo provare a collegare anche un display e veder cosa succede.

flz47655

Secondo me non puoi basarti su un termometro al mercurio.. probabilmente la temperatura più accurata è quella del sensore

Ciao

Go Up