Raspberry PIにPyCallをインストールしてRubyからGPIOのPython用ライブラリを使ってみる


はじめに

長らく放置していたラズパイを使って何かしようと思ったけど、テーマが思いつきません...(汗)

しばらく考えてみた結果、先日から利用しているPyCallがどのくらい汎用的に使用できるか試してみようということで、ラズパイにPyCallを入れてスイッチのON/OFFを検出する回路を作ってRubyで動かしてみました。

[参考サイト]
Raspberry Pi GPIO入出力のサンプル(Python, C言語, shellスクリプト)

PyCallのインストール

初期インストール直後にRuby2.1が入っていたので、これをそのまま利用します。
以下のコマンドでPyCallをインストール。

$ sudo apt install -y ruby-dev
$ sudo gem install --pre pycall

Python用のソースコードを確認

前述の参考サイトにて公開されているソースコードを見てみます。

gpio_input.py
#!/usr/bin/python

import RPi.GPIO as GPIO
import time

IO_NO = 4

print("press ^C to exit program ...\n")

GPIO.setmode(GPIO.BCM)
GPIO.setup(IO_NO, GPIO.IN)

try:
 while True:
  print(GPIO.input(IO_NO))
  time.sleep(1)
except KeyboardInterrupt:
 print("detect key interrupt\n")

GPIO.cleanup()
print("Program exit\n")

試しに実行してみると...

$ python gpio_input.py
press ^C to exit program ...
1
1
1
0
0
1
1
1
0
1
1
^Cdetect key interrupt

Program exit
$

ボタンを押すと0になって、離すと1が表示されるようです。
とりあえず配線は間違っていないことがわかりました。

PyCallを使って書き換え

サンプルコードをそのまま使うのでは少し味気ないので、ON/OFFした回数を数えながら表示するよう変更してみます。

gpio_input.rb
require 'pycall/import'
include PyCall::Import

pyimport 'RPi.GPIO', as: 'gpio'

io_no = 4

status = 1
buff = 1

cnt = 0

puts "press ^C to exit program ...\n"

gpio.setmode.(gpio.BCM)
gpio.setup.(io_no, gpio.IN)

# 「Ctrl」+「C」で停止させる
Signal.trap(:INT) do
  puts "detect key interrupt\n"
  gpio.cleanup.()
  puts "Program exit\n"
  exit 0
end

loop do
  status = gpio.input.(io_no)
  if buff != status
    if status == 1
      puts "OFF"
    else
      cnt += 1
      puts "ON(#{cnt})"
    end
  end

  buff = status
  sleep 0.5
end

ちなみに、Rubyでは大文字から始まる変数は定義できない(...と聞いたことがある)ので、小文字に変えて使っています。

動作確認

コマンドを実行し、ボタンを数回押してみる...

$ ruby gpio_input.rb
press ^C to exit program ...
ON(1)
OFF
ON(2)
OFF
ON(3)
OFF
^Cdetect key interrupt

Program exit
$

できた(^-^)

PI PiperというGemを使えばRubyでも問題なくできるようなので、PyCall使う必要はないんですけどね...

さて、次は何しようかな。