IoTで自動的に動く浴室内向けファンの昇降角度精度上げるという話であるが、以前投稿した記事と密接に関連しているのでこの記事単体でいきなり読んでもわからない人にはわからないかもしれない。
あまり知識に自信がない人は過去の記事を一読してからこちらを読むことをおすすめしておく。
以前投稿したブログ記事の追記となる
以前の記事は下記リンクを見てもらうとしてざっとここでも数行程度で内容に触れておく。
Raspberry Piが洗面所のすぐ外の壁にくっつけてあって、そいつが時間になるとサーボを回してリレーをオンしたりオフしたりするようにした。
リレーではファンのオンとオフを行い、サーボの回転によってウィンチとして働き、浴室ドアのすぐ上に板と蝶番で貼り付けたサーキュレーターが上がったり下がったりするように仕掛けをした。
ただどの位置で止まるかというのが定まらず、前回は適当に回転数を決めただけで終わりにした。
そして今回は板にスイッチを取り付けてスイッチを押したところで上がったときも下がったときも止まるようにした。つまり決めた位置できちっと止まるというわけだ。
用意した部品
マイクロスイッチ
オムロン マイクロスイッチ SS5GL
¥217(2022/03/07 20:53時点の価格)
平均評価点:
>>楽天市場で探す
>>Yahoo!ショッピングで探す
使ったのはこの写真のものではなく、たまたま手元にあったものを使ったがどんなのを使っても実現できるだろう。
上昇用と下降用で2個要る。
その他
ジャンプワイヤーだの平型ギボシだのは適当にあるやつを使ったので何をどれくらいという定量的な説明は省略する。
今回の作業手順
マイクロスイッチを引き込む
プログラム修正を先にやってもいい。
っていうか同時にやるのがいい。
Raspberry Piまで伸ばすリード線を必要な長さだけ確保してからマイクロスイッチに平型ギボシを取り付ける。
リード線の片側の端はマイクロスイッチにつける平型ギボシで、もう片側の端はRaspberry PiのGPIOにつけられるように加工する。ジャンプワイヤーのメスをはんだ付けするとか。
プログラム修正
プログラムを以下に載せておくけどあまり参考にしないでほしい。
#!/usr/bin/env python
# -*- coding: utf-8 -*-
#第1引数 "right"or "left"をつける
#第2引数 ループ回数(1回のループで90度回る)
import sys
import RPi.GPIO as GPIO
import time
args = sys.argv
GPIO.setwarnings(False)
GPIO.setmode(GPIO.BCM)
#GPIO PIN DEFINE
gp_out = 17
UP_LIMIT = 26 #←ここのポート番号は任意
DOWN_LIMIT = 5 #←ここのポート番号は任意
GPIO.setup(gp_out, GPIO.OUT)
#↓ここの構文参照先
#https://denkisekkeijin.com/raspberrypi/pi-sw/
GPIO.setup(UP_LIMIT,GPIO.IN, pull_up_down=GPIO.PUD_UP)
GPIO.setup(DOWN_LIMIT,GPIO.IN, pull_up_down=GPIO.PUD_UP)
servo = GPIO.PWM(gp_out, 50)
servo.start(0)
#time.sleep(1)
def servo_angle(angle):
duty = 2.5 + (12.0 - 2.5) * (angle + 90) / 180 #角度からデューティ比を求める
servo.ChangeDutyCycle(duty) #デューティ比を変更
#args1 = "right"
#args2 = 2
#for num in range(int(args[2])):
for num in range(int(args[2])):
if args[1] == "right": # サーボ右回転のとき(上昇)
if (0 == GPIO.input(UP_LIMIT)): # スイッチが入ると0になるようなのでこうした
for num2 in range(5): # スイッチ繋ぎっぱなしだと気持ち悪いので少し戻す
if(1 == GPIO.input(UP_LIMIT)):
break
servo_angle(-90)
break
servo_angle(90)
elif args[1] == "left": # サーボ左回転のとき(下降)
if (1 == GPIO.input(DOWN_LIMIT)):
for num2 in range(5):
if(0 == GPIO.input(DOWN_LIMIT)):
break
servo_angle(90)
break
servo_angle(-90)
time.sleep(0.5)
time.sleep(0.5)
servo.stop()
GPIO.cleanup()
マイクロスイッチの位置決め
動画でも話したんだけど、プログラムを作る手間よりマイクロスイッチの位置決めをして固定するほうが100倍ぐらい大変だ。
ハードウェアを作るって楽じゃないなってこういうふうに両方やるときに痛感するもんだ。
とにかくファンの板が下がったときと上がったときに適当なところでうまくスイッチが入るように位置を無理やり決めて取り付けないことにはこの機能が実現しないのでなんとかする。
実際のフローチャート
1 アレクサに指令する
これは特筆することはなくAlexaに定形アクションで命令するだけ。
定型文は自分で決める。たとえば「浴室ファンを起動して」など。
2 アレクサからNode-RED Alexa Home Bridgeへメッセージ
AlexaからRaspberry Piへ司令を伝達するのにNode-REDというサービスが今のところ無料で使えてかなり使い勝手が良いのでこれでいく。
Node-REDの使い方についての記事を前に書いてある。
3 Alexa BridgeからRaspberry Piへメッセージ
2と同じくNode-REDを使った処理になるのでここでは詳細な説明は割愛する。
同じ過去記事で多少説明しているのでそちらを参照されたい。一応少し説明しておく。
- Node-RED Alexa Home Skill Bridgeのサイトで機器(デバイス)を登録する
- Raspberry PiでNode-REDを常時起動しておく
- Raspberry Piでhttps://
:1880を開く(またはリモートパソコンからVNCでRaspberry Piにログインして開く) - Node-REDのノード設定をする
- 同じ画面上でデプロイ(展開・配置)する
4 Raspberry Piがサーボを動かす
これは前回から特に変化はない。
5 マイクロスイッチが押されたら停止
まずは新たに2個設置したスイッチのポートを適当に決める。マジで適当に決めたのだが本当はどこらへんがいいとかあるんかな?
スイッチだからそれぞれ2本コードが出ているが1本は下記のポート番号に接続して、もう一本はそれぞれどこかGNDに接続しておく。
UP_LIMIT = 26 #←ここのポート番号は任意
DOWN_LIMIT = 5 #←ここのポート番号は任意
マイクロスイッチが押されたかの判断を以下の条件文で行っている。
if(0 == GPIO.input(DOWN_LIMIT)):
でしていて、押されたらループを抜けるんだけどその前にスイッチが戻るまで数回転させておく。スイッチが押された状態で停止っていうのも気持ちわるいから。
それがこれ。
for num2 in range(5):
if(0 == GPIO.input(DOWN_LIMIT)):
break
servo_angle(90)
GoogleHomeで扱いたい場合
上記の手続きとほとんど同じではあるが多少の違いがあるのでここで述べておく。
- 機器(デバイス)の登録はこちら→Node-RED Google Assistant Bridgeのサイトから行うがほとんど操作は同じ
- Raspberry Pi上でのNode-RED手続きもほとんど同じだがメッセージの処理が少し違う
まとめ
以上のようなことで今までいい加減なところで止まってしまっていたファン取り付け板が毎朝毎晩決めた位置でピタっと止まるようになり大変気分が良い。
動画も公開中