"Đi học thoai": Phần 4 - Cảnh báo cháy với Raspberry Pi và Arduino

Mô tả dự án: 

Đây là bài biến thể từ "Đi học thoai" phần 1 (cảnh báo cháy với Raspberry Pi và Arduino) và Lồng tiếng cho Raspberry Pi. Nếu bạn đi học không có thời gian check email liên tục thì hệ thống sẽ phát cảnh báo cháy qua loa.

Nguyên lý

Ta dùng cảm biến nhiệt độ DS18820 đo nhiệt độ và gửi qua cổng USB serial. Raspberry Pi đọc nhiệt độ và nếu trên 60 thì sẽ phát tiếng cảnh báo với chương trình chuyển ngữ festival. 

Chuẩn bị

  •  Raspberry Pi hay Pizero
  • Raspberry Pi Camera Module
  • 1 Arduino 
  • 1 cảm biến DS18B20
  • Điện trở 4.7kOhm

Bạn nối theo như bài đã viết trên cộng đồng nha:http://arduino.vn/bai-viet/977-huong-dan-su-dung-cam-bien-nhiet-do-ds18b...

Sau đó nối Arduino với USB của Raspberry Pi là xong.

Code Arduino

#include <OneWire.h>

// OneWire DS18S20, DS18B20, DS1822 Temperature Example
//
// http://www.pjrc.com/teensy/td_libs_OneWire.html
//
// The DallasTemperature library can do all this work for you!
// http://milesburton.com/Dallas_Temperature_Control_Library

OneWire  ds(2);  // on pin 2CM0'CO (a 4.7K resistor is necessary)

void setup(void) {
  Serial.begin(9600);
}

void loop(void) {
  byte i;
  byte present = 0;
  byte type_s;
  byte data[12];
  byte addr[8];
  float celsius;
  
  if ( !ds.search(addr)) {
    Serial.println("No more addresses.");
    Serial.println();
    ds.reset_search();
    delay(250);
    return;
  }
  
  Serial.print("ROM =");
  for( i = 0; i < 8; i++) {
    Serial.write(' ');
    Serial.print(addr[i], HEX);
  }

  if (OneWire::crc8(addr, 7) != addr[7]) {
      Serial.println("CRC is not valid!");
      return;
  }
  Serial.println();
 
  // the first ROM byte indicates which chip
  switch (addr[0]) {
    case 0x10:
      Serial.println("Chip = DS18S20");  // or old DS1820
      type_s = 1;
      break;
    case 0x28:
      Serial.println("Chip = DS18B20");
      type_s = 0;
      break;
    case 0x22:
      Serial.println("Chip = DS1822");
      type_s = 0;
      break;
    default:
      Serial.println("Device is not a DS18x20 family device.");
      return;
  } 

  ds.reset();
  ds.select(addr);
  ds.write(0x44, 1);        // start conversion, with parasite power on at the end
  
  delay(1000);     // maybe 750ms is enough, maybe not
  // we might do a ds.depower() here, but the reset will take care of it.
  
  present = ds.reset();
  ds.select(addr);    
  ds.write(0xBE);         // Read Scratchpad

  Serial.print("Data = ");
  Serial.print(present, HEX);
  Serial.print(" ");
  for ( i = 0; i < 9; i++) {           // we need 9 bytes
    data[i] = ds.read();
    Serial.print(data[i], HEX);
    Serial.print(" ");
  }
  Serial.print("CRC=");
  Serial.print(OneWire::crc8(data, 8), HEX);
  Serial.println();

  // Convert the data to actual temperature
  // because the result is a 16 bit signed integer, it should
  // be stored to an "int16_t" type, which is always 16 bits
  // even when compiled on a 32 bit processor.
  int16_t raw = (data[1] << 8) | data[0];
  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];
    }
  } else {
    byte cfg = (data[4] & 0x60);
    
    // at lower res, the low bits are undefined, so let's zero them
    if (cfg == 0x00) raw = raw & ~7;  // 9 bit resolution, 93.75 ms
    else if (cfg == 0x20) raw = raw & ~3; // 10 bit res, 187.5 ms
    else if (cfg == 0x40) raw = raw & ~1; // 11 bit res, 375 ms
    
    //// default is 12 bit resolution, 750 ms conversion time
  }
  celsius = (float)raw / 16.0;
  
  Serial.print("Temperature = ");
  Serial.print(celsius);
  Serial.print(" Celsius, ");
}

Code trên Raspberry pi

Trước hết bạn phải tải chương trình festival về với sudo apt-get install thần thánh:

sudo apt-get install festival

Chép đoạn code sau và lưu lại với tên di_hoc_thoi_4.py.

#!/usr/bin/bash
#By MonsieurVechai
import time
import os, subprocess
import re, serial
'''
serial stuff returned:
    ROM = 22 D 8D 16 0 0 0 C9
    4B 46 7F FF 2 10 71  CRC=71
      Temperature = 22.87 Celsius, 73.18 Fahrenheit
      No more addresses.
'''


class ds18x20:
    def __init__(self):
        try:
            self.ser = serial.Serial('COM1', 9600, timeout=1)
        except:
            print "Cannot open serial port"
            exit(1)
        print "ds18x20 device serial link opened"    
        self.ser.flushInput()

    def readTemperature(self):
        isTemp = False
        while isTemp == False:
            line = self.ser.readline()
            if line.startswith("Temperature"):
                isTemp = True
                re_list = re.findall('\d+.\d+',line) # find the decimal numbers in the string and put to list using re (regular expression)
                temperature = float(re_list[0])
        return temperature

def close(self):
        self.ser.close()
        print 'Device closed'

def read_temperature():
    dev = ds18x20()
    #Sometimes IndexError happens and we need to take the temperature measurement again
    try:
     temp = dev.readTemperature()
    except IndexError:
     temp = dev.readTemperature()

    dev.close() #Have to close device after use
    return float(temp)


def main(): 
    dev = ds18x20()  
    print "Arduino is ready."

    try:       
        # Loop until users quit with CTRL-C
        while True :  
            # Read Temperature from Arduino
            temperature = read_temperature()
            print "Current Temperature: " + str(temperature)
            if temperature > 60:
                print "High temperature detected. Warning!!!"
                os.system('echo "Warning! Warning! Warning! Temperature is too high!"|festival --tts')
                   
    except KeyboardInterrupt:
        print "Quit program"
        
        
if __name__ == "__main__":
    main()

Gợi ý nâng cao

  • Kết hợp với các cảm biến khác như khí gas, nước.
  • Gắn thêm potentiometer để ngưỡng phát cảnh báo.
  • Gắn thêm 1 nút bấm để reset hệ thống.
lên
15 thành viên đã đánh giá bài viết này hữu ích.
Từ khóa: 
Các dự án được truyền cảm hứng

Select any filter and click on Apply to see results

Các bài viết cùng tác giả

Raspberry Pi Thiên Lý Nhãn (Phần 2): Nhận diện khuôn mặt với OpenCV

Bài này tui sẽ hướng dẫn các bạn dùng OpenCV khai thác sức mạnh tính toán của Raspberry Pi, cụ thể là trong việc nhận dạng khuôn mặt.

lên
16 thành viên đã đánh giá bài viết này hữu ích.

Raspberry Pi và Arduino. Tại sao không?

"Cuộc chiến" giữa Raspberry Pi và Arduino vẫn chưa đến hồi kết. Tuy nhiên câu hỏi đặt ra là 2 đồng chí này có nhất thiết phải như nước với lửa không? Bài này tui sẽ viết kinh nghiệm cá nhân về cách kết hợp giữa Arduino và Raspberry Pi trong cùng 1 dự án.

lên
25 thành viên đã đánh giá bài viết này hữu ích.