きっかけ
震災以来,会社で「節電要求」が厳しく,エアコンもぎりぎりまで絞られてしまい,会社の実験室が暑いため,管理部門に文句を言おうと思い,温度を自動で図る手段をarduinoで作ってみた.実現した機能
LM35DZという温度センサーを用いて,0℃~100℃の温度をシリアルモニターに摂氏で表示させるのと,httpでのアクセスで測定結果を摂氏で答える機能を入れてみた.ついでに,設定値以上に温度がなった場合は,基板上のLEDがつきっぱなしになるようにもなっている.参考URL
以下のようなwebの情報をみて作った.httpサーバおよび,温度センサ関連
http://openhardware.gridshield.net/home/arduino-snmp-temperature-sensor
http://d.hatena.ne.jp/a10i/20110607/1307453448
http://homepage3.nifty.com/sudamiyako/zk/AVR_ADC/AVR_ADC.html
pingのライブラリの情報
http://playground.arduino.cc/Code/ICMPPing
使ったハードウェア
Arduino Ethernet R3
あちこちで売っているけど,千石電商の店頭で買ったので,リンクも千石のものARDUINO-A000068スイッチサイエンスのUSBシリアルボード
電源供給とPCとのシリアル接続を兼ねてUSBインターフェースを追加.
FTDI USBシリアル変換アダプター(5V/3.3V切り替え機能付き)高精度IC温度センサ
これもあちこちで売っていると思うけどけど,秋月電子で買ったので,リンクも秋月のものLM35DZその他のパーツ(LEDなど)
他の部品は以前千石で買ったarduinoの初心者向けのパーツだけをまとめた部品キットのものを流用.ただし,キットのURLは見当たらない.回路
arduinoでは皆がEagle CADを使っているみたいなので,それで書いた回路図からイメージファイルに変換したものを張っておきます.Eagle CADの回路図
写真もつけておきますが,USBインターフェースは外したものになってます.
ソース
ソースコード(TemperatureWebServer.ino)は以下のようになってます.ソースが見づらいのは,また後で直します.
/*
LM35DZを用いた温度測定(0℃~100℃)
シリアルモニターに摂氏で表示させるのと,httpでのアクセスで答える
参考URL
httpサーバおよび,温度センサ関連
http://openhardware.gridshield.net/home/arduino-snmp-temperature-sensor
http://d.hatena.ne.jp/a10i/20110607/1307453448
http://homepage3.nifty.com/sudamiyako/zk/AVR_ADC/AVR_ADC.html
pingのライブラリ
http://playground.arduino.cc/Code/ICMPPing
*/
/* 固定IP設定の時に,pingで設定を確認する機能を有効にする場合に定義する */
#define USE_PING
#include <SPI.h>
#include <Ethernet.h>
#ifdef USE_PING
#include <ICMPPing.h>
#endif /* USE_PING */
/*
* 配線関連の定数
*/
int TempSensorPin = 0; // センサ用のアナログI/Fは0番を利用
boolean useLED = true; // インジケーター用LEDを用いる場合は true
/* 以下の定義は,インジケーター用のLEDを使わない場合は適当な整数で良い */
int RedPin=8; // 赤色は8番ピン
int GreenPin=9; // 緑色は9番ピン
/*
* デバッグ関連
*/
boolean debugFlag=true; // デバッグ目的で,各種情報をシリアルに出力する場合は true
/*
* 温度センサ関連の定数
*/
float v=5.0; // MEGA2560やEthernet R3は5.0V駆動
float tempC = 0; // 摂氏値( ℃ )
float Threshold=28.0; // 警告LEDをつける閾値(気温)
float offset = 0; // センサの温度ズレを修正する変数
/*
* ネットワーク関係の定数
*/
byte mac[] = { 0x90, 0xA2, 0xDA, 0x0F, 0x92, 0x1A }; //アドレスは手持ちのarduinoのものに変更すること
boolean useDhcp = false; // DHCPで運用する場合は true に変更
// DHCPでのアドレス取得失敗時の対策や,長時間経過後のアドレス再割当て等は対応していない
/* 以下は固定IP運用の場合の変数 */
IPAddress ip(192,168,0,10);
IPAddress dnsServer(192,168,0,1);
IPAddress gatewayAddress(192,168,0,1);
IPAddress netMask(255,255,255,0);
#ifdef USE_PING
SOCKET pingSocket = 0;
char buffer [256];
#endif /* USE_PING */
/*
* プログラム本体
*/
#ifdef USE_PING
ICMPPing ping(pingSocket, (uint16_t)random(0, 255));
#endif /* USE_PING */
EthernetServer server(80); // サーバオブジェクトの定義. 引数はポート番号
void setup()
{
if (debugFlag) {
// シリアル通信速度
Serial.begin(9600);
}
if (useLED) {
// LED用のピンの設定
pinMode(RedPin,OUTPUT);
pinMode(GreenPin,OUTPUT);
// LEDで起動がわかるよう,短時間点灯する
digitalWrite(RedPin,HIGH);
digitalWrite(GreenPin,HIGH);
delay(300);
digitalWrite(RedPin,LOW);
delay(300);
digitalWrite(GreenPin,LOW);
}
// MACアドレスとIPアドレスの設定
// 参考URL http://arduino.cc/en/Reference/EthernetBegin
if (useDhcp) {
if ((Ethernet.begin(mac)==0) && (debugFlag)) {
Serial.println(\"Failed to configure Ethernet using DHCP\");
}
} else {
Ethernet.begin(mac, ip, dnsServer, gatewayAddress, netMask);
#ifdef USE_PING
// ルータのアドレスにping
// 参考URL http://playground.arduino.cc/Code/ICMPPing
Serial.println(\"Manual ip confuguration of ethernet\");
ICMPEchoReply echoReply = ping(gatewayAddress, 4);
if (debugFlag) {
if (echoReply.status == SUCCESS) {
Serial.println(\"Ping to Gateway address : success\");
} else {
Serial.println(\"Ping to Gateway address : fail\");
}
}
#endif /* USE_PING */
}
if (debugFlag) {
// IPアドレスのシリアルへの出力
Serial.println(\"IP address of Ethernet Interface\");
Serial.println(Ethernet.localIP());
}
if (debugFlag) {
// 温度センサの温度取得テスト
Serial.println(\"testing temperature sensor : start\");
float temperature = getTemperature(TempSensorPin,false);
Serial.println(\"testing temperature sensor : done\");
}
// サーバの実行
server.begin();
}
void loop()
{
// 接続してきたクライアントを示すオブジェクトを生成
EthernetClient client = server.available();
if (client) {
if (debugFlag) {
Serial.println(\"Connection established by a client\");
}
// an http request ends with a blank line
boolean currentLineIsBlank = true;
while (client.connected()) {
if (client.available()) {
char c = client.read(); //一文字読み取り
// if you\'ve gotten to the end of the line (received a newline
// character) and the line is blank, the http request has ended,
// so you can send a reply
if (c == \'\\n\' && currentLineIsBlank) {
// send a standard http response header
client.println(\"HTTP/1.1 200 OK\");
client.println(\"Content-Type: text/html\");
client.println();
// 温度読み取り
float temperature = getTemperature(TempSensorPin,useLED);
client.print(\"Temperature: \");
client.print(temperature);
client.print(\" degrees Celsius\");
client.println(\"<br />\");
break;
}
if (c == \'\\n\') {
// you\'re starting a new line
currentLineIsBlank = true;
}
else if (c != \'\\r\') {
// you\'ve gotten a character on the current line
currentLineIsBlank = false;
}
}
}
// give the web browser time to receive the data
delay(1);
// close the connection:
client.stop();
}
}
//
// 温度読み取り関数
//
float getTemperature(int pin,int ledFlag){
float tmp;
if (ledFlag) {
digitalWrite(GreenPin,HIGH);
delay(500);
}
tmp = analogRead( pin );
tmp = ((v * tmp) / 1024) * 100;
tmp = tmp + offset;
if (debugFlag) {
// 温度のシリアルへの出力
Serial.println(\"temperature is\");
Serial.println(tmp);
}
if (useLED) {
digitalWrite(GreenPin,LOW);
if (tmp > Threshold ) {
digitalWrite(RedPin,HIGH);
} else {
digitalWrite(RedPin,LOW);
}
}
return tmp;
}
0 件のコメント:
コメントを投稿