Czujnik temperatury I2C LM75
Zasada działania
El IC LM75 to krzemowy, półprzewodnikowy czujnik temperatury pasma wzbronionego.
W półprzewodnikach tzw zakazany zespół Jest to strefa energetyczna elektronów, której nie można zwiększyć wraz ze wzrostem pola elektrycznego, ponieważ nie ma dostępnych stanów, w których można by poruszać się szybciej. Ten zakazany zespół jest zaliczany pomiędzy pasmo walencyjne (niższa energia) i zespół napędowy (wyższa energia). Wzbudzenie termiczne (wzrost temperatury, dla celów, które nas interesują) może spowodować, że niektóre elektrony uzyskają wystarczającą energię, aby przejść do zespół napędowy.
Jak wyjaśniono w poprzednim artykule na temat elektroniczny pomiar temperaturyw metalach, chociaż liczba nośników nie zależy od temperatury (wszystkie elektrony są zawsze dostępne), na ich ruchliwość wpływa temperatura, tak że opór w metalach rośnie wraz z temperaturą ze względu na spadek prędkości elektronów w wyniku wzrost ich mieszanie termiczne i rozpraszanie wytwarzanych przez to elektronów.
W przypadku półprzewodników, ze względu na obecność tego zakazany zespół Liczba nośników zależy od temperatury (w zależności od Rozkład Fermiego – Diraca) powodując wzrost przewodności wraz z temperaturą. W półprzewodnikach wzrost temperatury powoduje wzrost rezystancji, ale także (dalszy) wzrost przewodności.
L krzemowe półprzewodnikowe czujniki temperatury pasma wzbronionego, podobnie jak w przypadku LM75, działają zgodnie z tą zasadą, umożliwiając określenie temperatury poprzez ilościowe określenie jej wpływu na napięcie w diodzie krzemowej.
Komponenty sprzętowe LM75
LM75 posiada również przetwornik analogowo-cyfrowy wykorzystujący modulację Sigma-Delta który odpowiada za uzyskanie numerycznej (cyfrowej) wartości temperatury, wartości, która jest następnie zapisywana (co 100 ms) w jednym ze swoich rejestrów i z której można ją odczytać poprzez magistralę I2C.
Oprócz rejestru zawierającego zmierzoną temperaturę, LM75 posiada rejestr, w którym można zapisać temperaturę maksymalną, a także komparator, który jest w stanie wygenerować sygnał, jeśli zmierzona temperatura przekroczy temperaturę zapisaną w tym drugim rejestrze. Aby nie uruchamiać ponownie ostrzeżenia do czasu, gdy zmierzona temperatura spadnie poniżej pewnego poziomu, trzeci rejestr pozwala na zapamiętanie wartości temperatury histereza.
Konfiguracja pracy LM75 zapisana jest w czwartym rejestrze, za pomocą którego określane są warunki w jakich generowane jest ostrzeżenie, sposób uruchomienia tego sygnału ostrzegawczego (tryb przerwania lub tryb porównawczy) oraz załączenie urządzenia (tryb). normalna praca lub niskie zużycie paliwa) wśród innych parametrów.
Dane techniczne i wykonanie LM75
Zakres temperatur, które LM75 jest w stanie zmierzyć, waha się od -55°C do +125°C, a rozdzielczość numeryczna wynosi 0.125°C, chociaż dokładność wynosi w najlepszym przypadku tylko ±2°C, gdy temperatura mieści się w zakresie - 25°C do +100°C i dokładność ±3°C w najbardziej ekstremalnych temperaturach, od -55°C do +125°C.
Implementacja (sprzęt) LM75 w obwodzie jest bardzo prosta, nie wymaga więcej elementów niż rezystory podciągnięcie del autobus I2C i może być zasilany napięciem od 2,8 V do 5,5 V. W tym samym autobus I2C Można ustawić maksymalnie osiem termometrów LM75, konfigurując ich adres za pomocą trzech pinów A0, A1 i A2 na poziomie wysokim lub niskim, jak to zwykle bywa w takich przypadkach.
Z drugiej strony używanie LM75 jako sondy jest niewygodne ze względu na opakowania w jakich jest prezentowana, TSSOP (TSSOP8) Lub SEC (SO8) i jest zwykle używany do pomiaru temperatury otoczenia lub do pomiaru temperatury elementów rozmieszczonych w otoczeniu PCB w którym znajduje się termometr LM75.
Podczas uruchamiania LM75 jest skonfigurowany do wykrywania maksymalnej temperatury +80°C, czyli temperatury histereza +75°C oraz tryb pracy komparatora, czyli tryb emulujący pracę termostatu: uruchamia on ostrzeżenie w przypadku osiągnięcia temperatury maksymalnej i tylko wtedy, gdy spadnie ona poniżej histereza Regeneruje powiadomienie.
Eksploatacja LM75 z mikrokontrolera poprzez magistralę I2C
Dzięki wykorzystaniu autobus I2C Obsługa LM75 jest bardzo prosta, wystarczy wejść na adres zajmowany przez niego na magistrali, aby zapisać lub odczytać konfigurację i uzyskać wartość zmierzonej temperatury.
Adres I2C podstawa LM75 to 0B01001XXX i jest uzupełniona, jak wyjaśniono powyżej, trzema ostatnimi bitami adresu, które są ustawione sprzętowo z pinami A0, A1 i A2 na wysoki (wartość jeden) lub niski (wartość zero).
LM75 jako termometr
Rejestr przechowujący ostatnią zmierzoną temperaturę (TEMP) znajduje się pod adresem 0x00, rejestr konfiguracyjny (CONF) znajduje się pod adresem 0x01, rejestr przechowujący temperaturę histereza pod adresem 0x02, a maksymalna lub przekroczona temperatura (TOS) ma adres 0x03. Z wyjątkiem aktualnej temperatury (TEMP), wszystkie działają w trybie odczytu i zapisu.
Korzystając z przykładów kodu opracowanych dla Arduino (który stał się niemal uniwersalnym odniesieniem) działanie LM75 można dodatkowo wyjaśnić. Najbardziej podstawowym i użytecznym przykładem jest użycie LM75 jako termometru poprzez odczyt zapisu ostatniej zmierzonej temperatury.
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
|
#define DIRECCION_LM75 0B01001000 // Dirección del LM75 con A0, A1 y A2 a nivel bajo
#define TEMPERATURA_ACTUAL_LM75 0x00 // Registro que almacena la temperatura medida
//#define TIEMPO_CONVERSION_LM75 100 // El LM75 convierte la temperatura (AD) cada 100 ms así que el intervalo entre lecturas debe ser mayor.
#define TIEMPO_ENTRE_LECTURAS_DE_TEMPERATURA 3000 // Intervalo entre lecturas consecutivas de la temperatura en ms
#include <Wire.h>
int temperatura; // Valor de la temperatura actual cargado del LM75
void setup()
{
Serial.begin(9600); // Inicializar las comunicaciones serie (para mostrar en la consola el valor de la temperatura)
Wire.begin(); // Inicializar las comunicaciones I2C
}
void loop()
{
Wire.beginTransmission(DIRECCION_LM75); // Acceder al LM75 por su dirección en el bus I2C
Wire.write(TEMPERATURA_ACTUAL_LM75); // Solicitar la lectura del registro de la temperatura actual
Wire.endTransmission(); // Liberar el bus I2C
Wire.requestFrom(DIRECCION_LM75,2); // Pedir dos bytes (el valor del registro de la temperatura actual)
temperatura=(Wire.read()<<8)|Wire.read(); // Leer el primer byte, rotarlo 8 posiciones y añadir el valor del segundo byte
Wire.endTransmission(); // Liberar el bus I2C
Serial.println((float)temperatura/32/8,DEC); // Sólo son relevantes los 11 bits más significativos con una precisión de un octavo de grado (1/8 = 0.125 °C)
delay(TIEMPO_ENTRE_LECTURAS_DE_TEMPERATURA); // Esperar un poco antes de volver a leer la temperatura
}
|
Proces ten jest typowy podczas pracy z urządzeniem I2C:
- Dodaj bibliotekę I2C do kodu z
#include <Wire.h>
- Zainicjuj bibliotekę I2C przy
Wire.begin();
- Uzyskaj dostęp do czujnika temperatury LM75 za pomocą
Wire.beginTransmission(DIRECCION_LM75)
- Wyślij adres rejestru, do którego uzyskano dostęp za pomocą
Wire.write(REGISTRO)
- Zwolnij autobus I2C z
Wire.endTransmission()
- Uzyskaj ponownie dostęp do LM75
- Zażądaj wartości rejestru za pomocą
Wire.requestFrom(DIRECCION,CANTIDAD)
- Sprawdź, czy dane zostały odebrane za pomocą
Wire.available()
- Przeczytaj żądaną wartość
Wire.read()
(tyle razy, ile bajtów to składa się) - Chociaż nie jest to konieczne, po zakończeniu zwolnij przycisk autobus I2C
Oprócz zwykłego protokołu pozyskiwania lub przechowywania informacji w logach urządzenia za pomocą autobus I2CAby wykorzystać dane dostarczane przez LM75, należy wziąć pod uwagę format, w jakim wewnętrznie reprezentuje on temperaturę.
Uzyskanie wartości zapisanej w zapisach temperatury LM75
W linii 22 kodu z poprzedniego przykładu możesz zobaczyć, jak załadować informacje przechowywane w trzech rejestrach temperatury LM75. Wykorzystuje dwa bajty (16 bitów), z których tylko 11 najbardziej znaczących bitów jest prawidłowych. Aby odczytać temperaturę jako liczbę całkowitą (ze znakiem zakodowanym w dopełnienie dwójki) najbardziej znaczący bajt jest ładowany jako pierwszy do zmiennej int
de Arduino i jest obracany o 8 bitów w lewo, pozostawiając go w najbardziej znaczącej części int
. Następnie odczytywany jest drugi bajt i dodawany do zmiennej. int
z operacją OR
Interpretacja wartości temperatury obciążenia LM75
W linii 24 możesz zobaczyć jak interpretować wartość temperatury. Przede wszystkim należy podzielić przez 32 jako liczbę całkowitą (obrócić odpowiednie 11 bitów bez utraty znaku) i podzielić przez 8, czyli liczbę „kroków”, za pomocą których przedstawiana jest temperatura (oktawy stopnia) aby uzyskać wartość typu float
z odpowiednimi miejscami po przecinku. Ponieważ kompilatory (w tym toolchain de Arduino) zoptymalizuj dzielenie liczb całkowitych przez 32, nie jest konieczne zachowywanie znaku i „ręczne” obracanie bitów, ponieważ operacja nie jest (znacznie) szybsza.
Sprawdź odbiór danych z magistrali I2C
Chociaż poprzedni kod będzie działał bez problemów pomimo braku sprawdzenia, czy dane żądane przez urządzenie dotarły. autobus I2C, najbardziej ortodoksyjną (i zalecaną) rzeczą jest poczekać, aż dane dotrą w odpowiedniej liczbie. Ponieważ prędkość transmisji i odporność na błędy są więcej niż wystarczające, często spotyka się kod, w którym po prostu żąda się danych i odczytuje je bez czekania. W przypadku przykładów warto zrobić to w ten sposób, ponieważ nie odwracają one uwagi od głównej intencji, ale w przypadku kodu produkcyjnego wskazane jest zrobienie tego zgodnie z sugestią w siódmym punkcie listy procesu komunikacji I2C. Kod w poniższym przykładzie podkreśla zalecane zmiany w użyciu LM75 w fazie eksploatacyjnej.
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
|
#define DIRECCION_LM75 0B01001000 // Dirección del LM75 con A0, A1 y A2 a nivel bajo
#define TEMPERATURA_ACTUAL_LM75 0x00 // Registro que almacena la temperatura medida
//#define TIEMPO_CONVERSION_LM75 100 // El LM75 convierte la temperatura (AD) cada 100 ms así que el intervalo entre lecturas debe ser mayor.
#define TIEMPO_ENTRE_LECTURAS_DE_TEMPERATURA 3000 // Intervalo entre lecturas consecutivas de la temperatura en ms
#define TIMEOUT_I2C 30 // Esperar 30 ms antes de renunciar a leer el bus I2C
#include <Wire.h>
int temperatura; // Valor de la temperatura actual cargado del LM75
unsigned long cronometro_i2c; // Cronómetro para medir el tiempo de espera de la lectura del bus I2C (y cancelar la operación si se supera el máximo)
void setup()
{
Serial.begin(9600); // Inicializar las comunicaciones serie (para mostrar en la consola el valor de la temperatura)
Wire.begin(); // Inicializar las comunicaciones I2C
}
void loop()
{
Wire.beginTransmission(DIRECCION_LM75); // Acceder al LM75 por su dirección en el bus I2C
Wire.write(TEMPERATURA_ACTUAL_LM75); // Solicitar la lectura del registro de la temperatura actual
Wire.endTransmission(); // Liberar el bus I2C
Wire.requestFrom(DIRECCION_LM75,2); // Pedir dos bytes (el valor del registro de la temperatura actual)
cronometro_i2c=millis();
while(Wire.available()<2&&(unsigned long)(millis()–cronometro_i2c)>TIMEOUT_I2C); // Esperar a que lleguen dos bytes al bus I2C o pase el tiempo máximo para abandonar
if(Wire.available()==2) // Si han llegado dos bytes
{
temperatura=(Wire.read()<<8)|Wire.read(); // Leer el primer byte, rotarlo 8 posiciones y añadir el valor del segundo byte
}
Wire.endTransmission(); // Liberar el bus I2C
Serial.println((float)temperatura/32/8,DEC); // Sólo son relevantes los 11 bits más significativos con una precisión de un octavo de grado (1/8 = 0.125 °C)
delay(TIEMPO_ENTRE_LECTURAS_DE_TEMPERATURA); // Esperar un poco antes de volver a leer la temperatura
}
|
Skonfiguruj działanie LM75
Najbardziej podstawowa konfiguracja LM75 polega na ustaleniu maksymalnej temperatury, po której następuje wygenerowanie ostrzeżenia i histereza, który określi, kiedy zostanie dezaktywowany i można go powtórzyć. Aby skonfigurować te wartości, wystarczy zapisać je w odpowiednich rejestrach.
Podobnie jak bieżący zapis temperatury, temperatura maksymalna (ostrzeżenie) i histereza Wykorzystują dwa bajty, ale w przeciwieństwie do pierwszego, nie uwzględniają 11 bitów (ósemka stopnia), ale 9 (pół stopnia), tak że nawet jeśli zostałaby zapisana mniejsza wartość, brane byłyby pod uwagę tylko interwały o tej rozdzielczości.
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
|
#define DIRECCION_LM75 0B01001000 // Dirección del LM75 con A0, A1 y A2 a nivel bajo
#define TEMPERATURA_ACTUAL_LM75 0x00 // Registro que almacena la temperatura medida
#define TEMPERATURA_MAXIMA_LM75 0x03 // Registro que almacena la temperatura máxima (al superarla avisa cambiando el estado del pin OS) 80 °C al inicio
#define TEMPERATURA_HISTERESIS_LM75 0x02 // Registro que almacena la temperatura por debajo de la cual la máxima vuelve a generar un cambio en el pin OS (temperatura de histéresis) 75 °C al inicio
//#define TIEMPO_CONVERSION_LM75 100 // El LM75 convierte la temperatura (AD) cada 100 ms
#define TIEMPO_ENTRE_AVISOS_DE_TEMPERATURA 3000 // Intervalo entre avisos consecutivos de exceso de temperatura en ms
#define TIMEOUT_I2C 30 // Esperar 30 ms antes de renunciar a leer el bus I2C
#define TEMPERATURA_AVISO 32.5 // Avisar a los 32.5 °C (Solamente se consideran 9 bits, es decir, medios grados)
#define TEMPERATURA_HISTERESIS 31.0 // No volver a avisar (a los 32.5 °C) hasta que no se baje a los 31.0 °C
#define PIN_AVISO_LM75 2 // Pin de Arduino al que se conecta la salida OS del LM75
#include <Wire.h> // Cargar la librería de las comunicaciones I2C
int temperatura; // Valor de la temperatura actual cargado del LM75
unsigned long cronometro_i2c; // Cronómetro para medir el tiempo de espera de la lectura del bus I2C (y cancelar la operación si se supera el máximo)
unsigned long cronometro_avisos=0; // Cronómetro para controlar que se avise del exceso de temperatura a un intervalo máximo (como máximo cada TIEMPO_ENTRE_AVISOS_DE_TEMPERATURA)
void setup()
{
pinMode(PIN_AVISO_LM75,INPUT); // Usar como entrada el pin de Arduino al que se conecta la salida OS del LM75
Serial.begin(9600); // Inicializar las comunicaciones serie
Wire.begin(); // Inicializar las comunicaciones I2C
//Configurar la temperatura de aviso
Wire.beginTransmission(DIRECCION_LM75); // Iniciar la comunicación con el LM75
Wire.write(TEMPERATURA_MAXIMA_LM75); // Acceder al registro que almacena la temperatura máxima (temperatura de aviso)
Wire.write((byte)((int)(TEMPERATURA_AVISO*8.0)>>3)); // Desplazar 5 bits a la izquierda y 8 a la derecha
Wire.write((byte)((int)(TEMPERATURA_AVISO*8.0)<<5)); // Desplazar 5 bits a la izquierda
Wire.endTransmission(); // Liberar el bus I2C
//Configurar la temperatura de histéresis
Wire.beginTransmission(DIRECCION_LM75); // Iniciar la comunicación con el LM75
Wire.write(TEMPERATURA_HISTERESIS_LM75); // Acceder a la temperatura de histéresis
Wire.write((byte)((int)(TEMPERATURA_HISTERESIS*8.0)>>3)); // Desplazar 5 bits a la izquierda y 8 a la derecha
Wire.write((byte)((int)(TEMPERATURA_HISTERESIS*8.0)<<5)); // Desplazar 5 bits a la izquierda
Wire.endTransmission(); // Liberar el bus I2C
// El aviso se activará cuando la temperatura sea TEMPERATURA_AVISO o superior
// y no se desactivará hasta que sea TEMPERATURA_HISTERESIS o inferior
}
void loop()
{
if(!digitalRead(PIN_AVISO_LM75)) // Si la señal OS del LM75 está a nivel bajo (polaridad por defecto del aviso)
{
if((millis()–cronometro_avisos)>TIEMPO_ENTRE_AVISOS_DE_TEMPERATURA) // Si ha transcurrido el tiempo entre avisos (además de estar activa la señal)
{
cronometro_avisos=millis(); // Reiniciar el cronómetro de aviso de la temperatura
Wire.beginTransmission(DIRECCION_LM75); // Acceder al LM75 por su dirección en el bus I2C
Wire.write(TEMPERATURA_ACTUAL_LM75); // Solicitar la lectura del registro de la temperatura actual
Wire.endTransmission(); // Liberar el bus I2C
Wire.requestFrom(DIRECCION_LM75,2); // Pedir dos bytes (el valor del registro de la temperatura actual)
cronometro_i2c=millis(); // Iniciar el cronómetro que controla si ha pasado el tiempo máximo de espera de recepción de datos desde el bus I2C
while(Wire.available()<2&&(unsigned long)(millis()–cronometro_i2c)>TIMEOUT_I2C); // Esperar a que lleguen dos bytes al bus I2C o pase el tiempo máximo para abandonar
if(Wire.available()==2) // Si han llegado dos bytes
{
temperatura=(Wire.read()<< 8)|Wire.read(); // Leer el primer byte, rotarlo 8 posiciones y añadir el valor del segundo byte
Serial.println((float)temperatura/32/8,DEC); // Sólo son relevantes los 11 bits más significativos con una precisión de un octavo de grado (1/8 = 0.125 °C)
}
Wire.endTransmission(); // Liberar el bus I2C
}
}
}
|
Ponieważ w poprzednim kodzie zmieniona została jedynie konfiguracja temperatur związanych z ostrzeżeniem, dalsza część operacji odpowiada konfiguracji domyślnej.
W tej konfiguracji domyślnej istotne są dwie charakterystyki, po pierwsze tryb ostrzegania, domyślnie nazywany „trybem termostatu”, który polega na aktywowaniu ostrzeżenia po osiągnięciu maksymalnej temperatury (lub ostrzeżeniu) i wyłączeniu go dopiero po osiągnięciu temperatura histereza. Alternatywą jest „tryb przerwania”, w którym sygnał zostaje załączony w przypadku przekroczenia wartości maksymalnej lub osiągnięcia wartości niższej od wartości histereza i jest resetowany poprzez odczyt dowolnego zapisu, zwykle aktualnej temperatury.
Drugą cechą jest to, że sygnał ostrzegawczy jest aktywowany na niskim poziomie, to znaczy pin OS znajduje się na wysokim poziomie, aż do osiągnięcia maksymalnej temperatury ostrzegawczej. Ponieważ polaryzacja sygnału ostrzegawczego (poziom, przy którym jest on aktywowany) jest konfigurowalna, w niektórych prostych instalacjach wystarczy użyć tego sygnału (sprzętu) do wykorzystania LM75, na przykład do podłączenia lub odłączenia wentylatora, gdy system osiąga określoną temperaturę.
Możliwe jest również skonfigurowanie działania LM75 w taki sposób, aby ostrzegał nie natychmiast po osiągnięciu temperatury ostrzegawczej, ale po kilku zdarzeniach. To zachowanie jest bardzo przydatne podczas pracy w temperaturze granicznej lub gdy zmienia się ona bardzo szybko. LM75 można skonfigurować tak, aby ostrzegał po przekroczeniu maksymalnej temperatury jeden, dwa, cztery lub sześć razy.
W rejestrze konfiguracyjnym znajduje się także bit umożliwiający dezaktywację („wyłączenie”) LM75 i przejście w tryb niskiego zużycia energii, z którego wychodzi się poprzez ponowną zmianę tego bitu lub po prostu podczas odczytu następnego rejestru.
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
|
#define DIRECCION_LM75 0B01001000 // Dirección del LM75 con A0, A1 y A2 a nivel bajo
#define TEMPERATURA_ACTUAL_LM75 0x00 // Registro que almacena la temperatura medida
#define TEMPERATURA_MAXIMA_LM75 0x03 // Registro que almacena la temperatura máxima (al superarla avisa cambiando el estado del pin OS) 80 °C al inicio
#define TEMPERATURA_HISTERESIS_LM75 0x02 // Registro que almacena la temperatura por debajo de la cual la máxima vuelve a generar un cambio en el pin OS (temperatura de histéresis) 75 °C al inicio
#define CONFIGURACION_LM75 0x01 // Registro del LM75 que almacena la configuración. El valor por defecto es cero
#define ENCENDER_LM75 0B00000000 // Encender el LM75 almacenando este valor (OR el resto) en el registro de configuración
#define APAGAR_LM75 0B00000001 // Apagar el LM75 (modo de bajo consumo) almacenando el valoren el registro de configuración
#define AVISO_LM75_COMPARAR 0B00000000 // Activo cuando se supera la temperatura máxima inactivo cuando la temperatura es menor que la de histéresis (modo termostato)
#define AVISO_LM75_INTERRUPCION 0B00000010 // Activo cuando se supera la temperatura máxima. Se resetea al leer el valor. No se volverá a activar hasta que no se alcance (primero) la de histéresis
#define AVISAR_LM75_BAJO 0B00000000 // Establece el nivel bajo en el pin OS cuando se supere la temperatura máxima
#define AVISAR_LM75_ALTO 0B00000100 // Establece el nivel alto en el pin OS cuando se supere la temperatura máxima
#define AVISAR_LM75_A_1 0B00000000 // Avisar cuando se supere una vez la temperatura (con riesgo de que un error producido por ruido en la conversión lance un aviso incorrecto)
#define AVISAR_LM75_A_2 0B00001000 // Avisar de temperatura superada cuando se mida dos veces
#define AVISAR_LM75_A_4 0B00010000 // Avisar de temperatura superada cuando se mida cuatro veces
#define AVISAR_LM75_A_6 0B00011000 // Avisar de temperatura superada cuando se mida seis veces
//#define TIEMPO_CONVERSION_LM75 100 // El LM75 convierte la temperatura (AD) cada 100 ms
#define TIEMPO_ENTRE_LECTURAS_DE_TEMPERATURA 2000 // Intervalo entre lecturas de la temperatura en ms
#define TIMEOUT_I2C 30 // Esperar 30 ms antes de renunciar a leer el bus I2C
#define TEMPERATURA_AVISO 32.5 // Avisar a los 32.5 °C (Solamente se consideran 9 bits, es decir, medios grados)
#define TEMPERATURA_HISTERESIS 31.0 // No volver a avisar (a los 32.5 °C) hasta que no se baje a los 31.0 °C
#define PIN_AVISO_LM75 7 // Pin de Arduino al que se conecta la salida OS del LM75
#include <Wire.h> // Cargar la librería de las comunicaciones I2C
int temperatura; // Valor de la temperatura actual cargado del LM75
unsigned long cronometro_i2c; // Cronómetro para medir el tiempo de espera de la lectura del bus I2C (y cancelar la operación si se supera el máximo)
unsigned long cronometro_avisos=0; // Cronómetro para controlar que se avise del exceso de temperatura a un intervalo máximo (como máximo cada TIEMPO_ENTRE_AVISOS_DE_TEMPERATURA)
void setup()
{
pinMode(PIN_AVISO_LM75,INPUT); // Usar como entrada el pin de Arduino al que se conecta la salida OS del LM75
Serial.begin(9600); // Inicializar las comunicaciones serie
Wire.begin(); // Inicializar las comunicaciones I2C
// El aviso se activará, a nivel alto (AVISAR_LM75_ALTO), cuando la temperatura sea TEMPERATURA_AVISO o superior cuatro veces consecutivas (AVISAR_LM75_A_4, que vale 0B00010000)
// y no se desactivará hasta que sea TEMPERATURA_HISTERESIS o inferior
// Configurar la temperatura de aviso
Wire.beginTransmission(DIRECCION_LM75); // Iniciar la comunicación con el LM75
Wire.write(TEMPERATURA_MAXIMA_LM75); // Acceder al registro que almacena la temperatura máxima (temperatura de aviso)
Wire.write((byte)((int)(TEMPERATURA_AVISO*8.0)>>3)); // Desplazar 5 bits a la izquierda y 8 a la derecha
Wire.write((byte)((int)(TEMPERATURA_AVISO*8.0)<<5)); // Desplazar 5 bits a la izquierda
Wire.endTransmission(); // Liberar el bus I2C
// Configurar la temperatura de histéresis
Wire.beginTransmission(DIRECCION_LM75); // Iniciar la comunicación con el LM75
Wire.write(TEMPERATURA_HISTERESIS_LM75); // Acceder a la temperatura de histéresis
Wire.write((byte)((int)(TEMPERATURA_HISTERESIS*8.0)>>3)); // Desplazar 5 bits a la izquierda y 8 a la derecha
Wire.write((byte)((int)(TEMPERATURA_HISTERESIS*8.0)<<5)); // Desplazar 5 bits a la izquierda
Wire.endTransmission(); // Liberar el bus I2C
// Configurar el número de veces que debe superarse la temperatura para generar un aviso y la polaridad del aviso
Wire.beginTransmission(DIRECCION_LM75); // Iniciar la comunicación con el LM75
Wire.write(CONFIGURACION_LM75); // Acceder al registro de configuración
Wire.write(AVISAR_LM75_ALTO|AVISAR_LM75_A_4); // Componer la configuración con operaciones OR sobre los diferentes (bits) valores
Wire.endTransmission(); // Liberar el bus I2C
}
void loop()
{
if((millis()–cronometro_avisos)>TIEMPO_ENTRE_LECTURAS_DE_TEMPERATURA) // Si ha transcurrido el tiempo entre lecturas
{
cronometro_avisos=millis(); // Reiniciar el cronómetro de aviso de la temperatura
Wire.beginTransmission(DIRECCION_LM75); // Acceder al LM75 por su dirección en el bus I2C
Wire.write(TEMPERATURA_ACTUAL_LM75); // Solicitar la lectura del registro de la temperatura actual
Wire.endTransmission(); // Liberar el bus I2C
Wire.requestFrom(DIRECCION_LM75,2); // Pedir dos bytes (el valor del registro de la temperatura actual)
cronometro_i2c=millis(); // Iniciar el cronómetro que controla si ha pasado el tiempo máximo de espera de recepción de datos desde el bus I2C
while(Wire.available()<2&&(unsigned long)(millis()–cronometro_i2c)>TIMEOUT_I2C); // Esperar a que lleguen dos bytes al bus I2C o pase el tiempo máximo para abandonar
if(Wire.available()==2) // Si han llegado dos bytes
{
temperatura=(Wire.read()<<8)|Wire.read(); // Leer el primer byte, rotarlo 8 posiciones y añadir el valor del segundo byte
Serial.print(“Temperatura “);
if(digitalRead(PIN_AVISO_LM75)) // Si la señal OS del LM75 está activa (a nivel alto)
{
Serial.print(“demasiado alta”);
}
else
{
Serial.print(“correcta”);
}
Serial.print(” (“);
Serial.print((float)temperatura/32/8,DEC); // Sólo son relevantes los 11 bits más significativos con una precisión de un octavo de grado (1/8 = 0.125 °C)
Serial.println(“)”);
}
Wire.endTransmission(); // Liberar el bus I2C
}
}
|
Zamieść komentarz