IOT:ラズベリーパイでサーボドライバPCA9685を使ってみる

Keita_Nakamoriです。

前回はサーボモータSG92Rをラズパイに直結して動かしてみました。

今回はサーボモータを16個同時に動かすことができるサーボドライバPCA9685を使って、SG90とSG92Rを同時に動かしてみようと思います。

 

動画

基本スペック

  • I2C周波数範囲:24-1526Hz
  • 動作電圧:2.3-5.5V
  • 入出力の許容電圧:5.5V
  • 最大62個のPCA9685が接続できます¥。よって992個のサーボモータを同時に動かせます。

余談:I2Cはアイ スクウエア シーと呼ぶそうです。

ピン

左端のピン

は、上から

  • GND:ラズパイGIPIOのグランドに接続する
  • DE:??? どこにも繋げない
  • SCL:シリアル通信のクロック ラズパイGIPIOのSCL1に繋ぐ
  • SDA:シリアル通信のデータ   ラズパイGPIOのSDA1に繋ぐ
  • VCC:プラス電圧 ラズパイGPIOの+5Vに繋ぐ
  • V+:??? どこにも繋げない

下端のピン

はサーボモータを接続します、左から0~15番が振られてあり合計16個のサーボモータと接続できます。

上から、

  • PWM:サーボモータのPWM=オレンジ
  • V+:サーボモータの赤
  • GND:サーボモータの茶

上端のコネクタ

は、電源供給です。

  • 左はV+:ラズパイの5Vに繋ぎます
  • 右はGND:ラズパイのGNDに繋ぎます
  • 今回はラズパイのGPIOに繋ぎましたが、16個サーボモータを繋げるときは、別途電源を取らなくてはならないと思います。

制御の話

  • PCA9685はPWMで動きます。
  • パルス幅によってサーボモータの回転角が0~180degが決定されます。
    • 例えば 0.5ms幅のとき0deg、1.5ms幅のとき90deg、2.5ms幅のとき180degになったりします。(周波数で変更できます。周波数が高いほうが高速で制御できます。)
  • アナログサーボの周波数範囲は30~60Hzのものがほとんどです。
  • 例えば、周波数f=60Hzのとき周期はT=1/f=17ms です。(早い方がいいので60Hzで考えましょう。)
  • 周期Tの分解能は12bitなので、周期Tを2^12=4096分割できます。1分割分を1ステップと呼ぶことにしましょう。
  • 周期17msを4096分割できるので、1ステップあたり0.004150390625ms になります。
  • パルス幅を0.5msにしたければ、ステップは0.5/(17/4096)=120.47058823529412ステップになります。
  • サーボモータ角度をodegにしたいときは0.5msですから、120ステップをONして、残りの(4096-120)をOFFにすれば良いのです。
サーボ回転角度[deg] ONの時間 [ms]  ステップ数
0 0.5 120
60 1.0 240
90 1.5 361
120 2.0 481
180 2.5 602
  • サーボ回転角度を0degから180degにするためには、(602-120)=482ステップになります。
  • 1degあたりのステップ数は 482ステップ/180deg = 2.7 (step/deg)
  • なので任意のサーボ回転角度θでステップ数Nsを表現すると、Ns=120+2.7θ ということになります。

モジュール Adafruit_PCA9685

pip3 install Adafruit_PCA9685 したところ拒否されました。

pipのバージョンを上げて再チャレンジします。

pip3 install –upgrade pip3 と書いたところ pip3でなくてpipで書けみたいなことを言われました。

pip install –upgrade pip と書いたところ許可がないといっております。

なので、スーパーDOしてみます。

sudo pip install –upgrade pip これでOKでした

Successfully uninstalled pip-19.0.3
Successfully installed pip-19.1.1

そして再度チャレンジ

pip3 install Adafruit_PCA9685  [Errno 13] 許可がありません

なるほど読めました。やはり須藤ですね。

sudo pip3 install Adafruit_PCA9685

Successfully installed Adafruit-GPIO-1.0.3 Adafruit-PCA9685-1.0.1 adafruit-pureio-0.2.3

これでやっとAdafruit_PCA9685モジュールがインストールできました。

pip freezeすると

Adafruit-GPIO==1.0.3
Adafruit-PCA9685==1.0.1
Adafruit-PureIO==0.2.3

が入っていました。注意点として、importするときはAdafruitの後ろにはハイフンではなくアンダースコアになります。

スクリプト

余談

ラズパイの操作はWindowsマシンからrealVNC Viewerでリモートしているのですが、ラズパイ側のidleに書いたスクリプトをcnt+c しても Windows側にcnt+v できません。

コツがありまして、ラズパイ側のText Editorに一旦貼り付けた後に、それをcnt+cしてから、Windows側にcnt+v すると、しっかりと貼り付けられます。

どうぞお試しあれ。

IOT:ラズベリーパイでサーボモータSG92Rを動かす

どーもこんにちはKeita_Nakamori(´・ω・`)です。

今日は、GPIOでサーボモータを動かして見ようと思います。

デバイス

サーボモータ:SG92R

配線

  1. サーボの茶をGND(グランド)
  2. サーボの赤を電源+5V
  3. サーボのオレンジは制御パルス用なので、今回はGPIO18に接続しました。

ラズパイの電源は5Vバッテリー2.1Aです。

※サーボの挙動がガクガクしています。電源のせいかも・・・

テストスクリプト

 

IOT:ラズベリーパイにVNC接続してOpenCVで顔認識する

どーもこんにちはKeita_Nakamori(´・ω・`)です。

 

前回、ラズベリーパイにVNC接続してOpenCVでカメラの起動に成功しました。

今回は更に、そのOpenCVで顔認識も追加していこうと思います。

bcm2835-v4l2 の自動化

前回ハマりました、bcm2835-v4l2 についてですが、やはりシャットダウンすると、無効になってしまい、OpenCVが機能しませんでした。

今回は、まず起動したときに自動的にbcm2835-v4l2 が実行される方法からやっていきます。

/etc/modules を開くと

# /etc/modules: kernel modules to load at boot time.
#
# This file contains the names of kernel modules that should be loaded
# at boot time, one per line. Lines beginning with “#” are ignored.

i2c-dev

と書いてありますが、これは”ブートするときにロードするためのカーネルモジュール群” を書いておく場所になっています。Windowsでいうとスタートアップです。

ここにbcm2835-v4l2をいれればOKなのですが、このファイルは書き込み禁止なので、予め解除しておきます。

ファイル書き込み禁止を解除する

パーミッションを確認します。

pi@pi:/etc $ ls -l modules

-rw-r–r– 1 root root 203 3月 23 20:29 modules

スーパーユーザーsudoとしてチェンジモードchmodして、パーミッションを777にします。

pi@pi:/etc $ sudo chmod 777 modules

で、変更が成功したか確認すると
pi@pi:/etc $ ls -l modules

-rwxrwxrwx 1 root root 203 3月 23 20:29 modules

フルアクセスに変更されました。

その上で、チェンジディレクトリcd /etc/でvimでmodulesを開きます。

pi@pi:/etc $ vim modules

i2c-devの下にbcm2835-v4l2を追加して保存しましょう。

# /etc/modules: kernel modules to load at boot time.
#
# This file contains the names of kernel modules that should be loaded
# at boot time, one per line. Lines beginning with “#” are ignored.

i2c-dev
bcm2835-v4l2

キャットで確認すれば

pi@pi:/etc $ cat modules

しっかりとbcm2835-v4l2が追加されているのがわかると思います。

本題:Opencvで顔認識をやってみる

基本的には、前回のコードに学習済みハールカスケードと顔認識した顔に四角い図形でマーキングをするスクリプトを追加するだけです。

まずhaarcascade_frontalface_alt2.xmlは/usr/local/share/OpenCV/haarcascades/ の中に入っているので、作業ディレクトリであるhome/pi/の中へコピーを作っておきます。

以上、簡単ですね。

IOT:ラズベリーパイにVNC接続してOpenCVで cv2.VideoCapture(0)してみる

どーもこんにちはKeita_Nakamori(´・ω・`)です。

今日は、WindowsマシンからラズベリーパイにVNC接続してOpenCVで cv2.VideoCapture(0)に挑戦します。

まずはrealVNC viewerを起動してIPアドレスを打ってVNC接続します。

1回つなげたことのあるIPアドレスは保存され、アイコンみたいに表示されるので2回目からはアイコンをクリックするだけの簡単操作でした。

落とし穴

早速ハマりました。cap=cv2.VideoCapture(0)してもcapにはなにもデータが入ってきません。ふぁ~(*´Д`)

ret, img = cap.read() しても、当然imgはNoneです。

なぜだ!

思い出しました

そう、かつてハマりまくった、あのときを・・・

ラズパイ専用カメラをしようしているので、一般的なwebカメラとして認識できるように下記のコードを実行することが必要でした。

注意点としては 最後の部分は 「ぶい よん える に」 です。

「ぶい よん いち に」 だと思って奮闘してしまいました。

sudo modprobe bcm2835-v4l2

ということで、shellでsudo modprobe bcm2835-v4l2と打ってカメラを認識させます。

テストコードを実行すると・・・

はい、隣の部屋のソファーが写っています。

弱点

ラズパイはwifi接続、Windowsマシンは有線ですが、VNC解像度をミディアムにしても、カメラのキャプチャー映像はガックガク!!です。

低解像度だと色がキッタナイ!

どうにもなりません。

念の為、試運転のコードを貼っておきます。

 

 

IOT:Python socketモジュールで通信してみる

どーも こんちには Keita_Nakamori (´・ω・`) です

今日は、socketモジュールを使ってみます。

前回、少しsocketモジュールについて基本的な操作をやりましたが、実際に運用するとなると不備が多いので、そこを修正していきます。

IT用語 (予備知識)

ポート

ネットワーク内の端末間でデータをやり取りする港(port)です。

ポート番号

ポートの番号です。TPCでデータをやり取りするとき、データは1プロセスとか1スレッドというプログラムの塊を対象とします。そのプロセスにはポート番号が割り当てられそこを通ってデータをやり取りします。

IPアドレスが住所なら、ポート番号はマンションの部屋番号みたいなものです。

よく使う番号をピックアップしてみます。

  • TCP 20 : FTP (データ)
  • TCP 22 : SSH
  • TCP 25 : SMTP
  • TCP 80 : HTTP
  • TCP 443 : HTTPS

ポート番号の種類

ポート番号は0から65535まで存在します。その中でも3つの種類に分けれれます。

ウェルノウンポート番号 0~1023

よく知られているポート番号という名前の通り、TPC/IP通信において主要なサービスがすでに使用しているポート番号です。ユーザーがここをいじってしまうと不具合が生じるので触らないでおきましょう。

レジスタードポート番号 1024~49151

特定のアプリケーションなどが使用することになっている番号です。IANAという団体が管理しているので、使うときは申請しなくてはいけません。

その他のポート番号 49152~65535

ユーザが自由に使って良いポート番号です。しかし、やたらと開放してはいけません。必要なものだけ開けましょう。

スクリプト

続きはあとで書きます。

IOT:python LINE Notify に メッセージを送る

どーも こんちには Keita_Nakamori (´・ω・`) です

PythonからLINE Notifyにメッセージを送るということをやってみようと思います。後々IOTの一環で、設備などの状態を監視し、故障予測の通知をしていくためにやってみました。

 

LINE notifyのAPI ドキュメント

LINE notifyのAPI ドキュメントをみるとやり方が書いてありますので、その通り進めました。通常のLINEアカウントがあればOKです。

予めトークンを取得しておいてください。

スクリプト

下記コードの<ここにアクセストークンを入れる>へ代入してください。< >は要りません。Bearerとの間にはスペースを一つ入れてください。

messageをmassageとミスタイプして焦らないでください。(わたしです)

実行すると下記のように自分のラインへアラートが来ます。

実行結果

IOT:python requestsモジュールを使ってみる

こんにちは Keita_Nakamori(´・ω・`)です。

今日は python urllib.requetsモジュールに続きまして requestsモジュールを使ってみようと思います。名称がとても似ていますが別物です。

前回のurllib.requestがpython標準モジュールであるのに対して、
今回のrequestsモジュールは標準ではなく、より使いやすく改良されています。
エンコードなども自動でやってくれるので、こちらのほうが圧倒的に人気があります。

JSONをディクショナリで取り出すときは requests.json() があるので jsonモジュールも不要です。

IT用語 予備知識

HTTPステータスコード

HTTPにおいてWebサーバからのレスポンスの意味を表現する3桁の数字からなるコードです。例えば、200はリクエストに対して正常にレスポンスが得られたという意味になります。

requestsモジュール

GET

POST

PUT

DELETE

 

 

IOT:python urllib.request を使ってみる

こんちには Keita_Nakamoriです。

Python標準モジュールのurllibを使ってHTTPメソドを実行してみましょう。

IT用語 (予備知識として)

HTTPメソド

クライアントからサーバーに命令をする具体的なやり方のことです。

基本の4つの操作
GET:データを参照する
POST:データを新規登録する(パスワードを見えないように送るとき)
PUT:データを更新する
DELETE:データを削除する

その他 HEAD OPTIONS TRACE PATCH LINK UNLINK と色々あります。

REST

-REpresentational State Transfer

”表現文の転送”ということでしょうか。Webサービスに対してデータをやり取りする際の取り決め、というかコンセプトです。

RESTに従ったWebサービスは、HTTPメソドの形式でアクセスすることでデータの送受信を行えます。

REST APIという形でまとまっているWebサービスが多いので利用できます。

パケット通信

音声通話のように回線を占有するのではなく、
データを小さな単位に分割して送受信することで
複数のユーザーで同じ回線をシェアできる方法です。

送信されたデータは交換機の記憶メディアに一時的に蓄積されるので
相手の通信環境が悪くても、復帰したときにデータを受信できます。

ペイロード

パケット通信においてパケットに含まれるヘッダやトレーラなどの付加的情報を除いたデータ本体のことです。

パケットにはデータの転送先や転送経路などを制御するための情報を含むヘッダや、データの破損などを検査するトレーラなどの情報が、データそのもののほかに付加されて送られて来ます。

ペイロードは、こうした情報を対象に含めず、ユーザーが送信したいデータそのものを指し示す際に用いられます。

urllibモジュール

基本的な GET

パラメータを含んだGET

パラメータが見えないようにするPOST

PUT

DELETE

ここで、HTTPError: HTTP Error 405: METHOD NOT ALLOWED とエラーになりました。DELETEは用意されていないようです。

IOT:socket通信の超基本

socket 使っていきましょう。

socket通信とは

Socket通信とは複数のコンピュータが、ネットワークを介してデータをやりとるする時に用いる通信規格の一種です。

今お使いのPCをサーバーにして、同PCをクライアントとしローカルホスト接続してみましょう。

 

サーバー側

まず、サーバー側のスクリプトから起動します。

実行すると、クライアントからのデータ待ち状態になります。

出力:

サーバーはポートNO. 2000 にバインドされました

サーバーはクライアントをリスニング中です

クライアント側

クライアント側のスクリプトを実行して、サーバーへデータを送りましょう

出力:

サーバーへ接続しました
サーバーへデータを送信しました

サーバー側 再び

サーバー側がクライアントからのデータを受け取りました。

直後に、クライアントに対して受信の通知をします。

出力:

クライアントのアドレスを受信しました : (‘127.0.0.1’, 52256)
クライアントからのデータを受信しました : こんにちはサーバーさん。私はクライアントです
コネクションは閉じられました
サーバーソケットは閉じられました

クライアント側 再び

サーバーから送られてきた受信の通知を受け取りました。

出力:

サーバーからの受信確認が返ってきました : サーバーです。データをしっかり受け取りました

クライアントソケットを閉じました

課題

このスクリプトでは、送受信がシーケンスになっており厳密には同時ではありません。

同時にする仕組みとして、マルチスレッディングというのがありますので、次回やってみましょう。