照度センサーTSL25721の使い方

TSL25721 照度センサー センサー

照度センサーTSL25721から照度データを読み取る方法を紹介します。

I2C通信による読み取りはRaspberry Pi、プログラム言語はPythonで行います。サンプルプログラムでは、データ読み取りだけでなく測定条件設定も行っています。

TSL25721は、人の目の反応に近似した周囲光検知(ALS)が可能です。
可視光と赤外光を検知するCh0と、赤外光を検知するCh1の2種類のフォトダイオードを有しています。

上下限しきい値の設定による割り込みを使用して、ポーリングによるシステム効率の低下防止や、スリープモードによる低消費電力化などの機能があります。

準備

TSL25721の購入

TSL25721はDual Flat No Leadと呼ばれる形状です。
これを手ではんだ付けするのは厳しいのでモジュールの購入になると思います。

下の写真は秋月電子通商で購入したTSL25721モジュールです。今回はこのモジュールを使用して照度測定を行います。

TSL25721 モジュール写真

TSL25721モジュールとRaspberry Piの接続

接続図

ブレッドボードを使用したTSL25721モジュールとRaspberryPiの接続【I2C】

接続写真

ブレッドボードを使用したTSL25721の接続写真 1
ブレッドボードを使用したTSL25721の接続写真 2

Raspberry Piの通信設定とPythonの操作方法

Raspberry PiのI2C通信設定を有効にします。
下の記事でRaspberry Piの通信設定と、Pythonの基本操作を説明しています。

I2C通信プログラミング

プログラムコード

Pythonプログラムです。

import smbus
import time

#I2C設定
i2c = smbus.SMBus(1)
dev_addr = 0x39

#センサーの設定
ret = i2c.write_byte_data(dev_addr, 0x80|0x20|0x0F, 0x02)
ret = i2c.write_byte_data(dev_addr, 0x80|0x20|0x01, 0xF6)
ret = i2c.write_byte_data(dev_addr, 0x80|0x20|0x00, 0x02|0x01)

#繰り返し
while True:
    
    #データ読み込み
    uv = i2c.read_i2c_block_data(dev_addr, 0x80|0x20|0x14, 0x04)
    
    #データ変換
    ch0 = uv[1] << 8 | uv[0]
    ch1 = uv[3] << 8 | uv[2]
    
    #物理量(UV照度)に変換
    ch0 = ch0 / 16 / 19.0
    ch1 = ch1 / 16 / 10.8
    
    #表示
    print('ch0: ' + str(ch0))
    print('ch1: ' + str(ch1))
    
    #一時停止
    time.sleep(1)

プログラムの説明

  1. I2C通信の設定
  2. センサーの設定
  3. センサーから照度データを取得
  4. データを物理量に変換し画面に表示
  5. 3.~4.を繰り返します

1.I2C通信の設定

#I2C設定
i2c = smbus.SMBus(1)
dev_addr = 0x39

i2c = smbus.SMBus(1)
インスタンス生成です。使用するBus1を指定します。

dev_addr = 0x39
デバイスのアドレス指定です。TSL25721のアドレスは0x39(16進数)で、通信時に指定します。

LXTerminalからの「i2cdetect -y 1」コマンド入力で、アドレスが0x39であることを確認出来ます。

2.センサーの設定

#センサーの設定
ret = i2c.write_byte_data(dev_addr, 0x80|0x20|0x0F, 0x02)
ret = i2c.write_byte_data(dev_addr, 0x80|0x20|0x01, 0xF6)
ret = i2c.write_byte_data(dev_addr, 0x80|0x20|0x00, 0x02|0x01)

設定は write_byte_data(adr, reg, dat)関数を使用します。

第1引数 adr:I2C通信のアドレス
第2引数 reg:レジスタ(設定したい項目の記憶場所)
第3引数 dat :データ(レジスタに設定する内容)

レジスタの指定で毎回orしている0x800x20は、「コマンド」と「連続読み込み」を示します。
その後に続く0x0Fが設定するレジスタです。

詳細は、データシートの『Figure 22: Command Register』で確認できます。

COMMAND TYPE ADD
1 0 1 0 0 0 0 0

TYPEの指定は以下の様になります。「Auto-increment protocol transaction」を選択しています。

FIELD VALUE DESCRIPTION
00 Repeated byte protocol transaction
01 Auto-increment protocol transaction
10 Reserved — Do not use
11 Special function — See description below

サンプルプログラムでは、
・Controllレジスタ
・ALS_Timingレジスタ
・Enableレジスタ
この3つのレジスタ設定をしています。レジスタの設定内容は以下の通りです。

i2c.write_byte_data(dev_addr, 0x80|0x20|0x0F, 0x02)

0x0F(Controllレジスタ)
AGAIN[0:1](アナログブロックのゲイン ×1/×8/×16/×120)

0x02
AGAIN[1:0](10:16×gain

i2c.write_byte_data(dev_addr, 0x80|0x20|0x01, 0xF6)

0x01(ALS_Timingレジスタ)
ATIME[7:0](内部積分時間 2.73ms~699ms)

0xF6
ATIME[7:0](F6:27.3ms

i2c.write_byte_data(dev_addr, 0x80|0x20|0x00, 0x02|0x01)

0x00(Enableレジスタ)
PON(電源 Sleep/Idle)
AEN(ALS Idle → ALSinit or Wait)
WEN(ウェイトタイマー)
AIEN(ALS割り込みマスク)
SAI(割り込み後のスリープ)

0x02|0x01
PON(1:Sleep → Idleへ移行)
AEN(1:Idle → ALS initへ移行)
WEN(0:ウェイトタイマーOFF(デフォルト))
AIEN(0:マスクしない(デフォルト))
SAI(0:スリープしない(デフォルト))

Reserved SAI Reserved AIEN WEN Reserved AEN PON
0 0 0 1 1

電源投入後はアイドル状態なので、初期設定後にALSに移行します。
コマンドによって、スリープ状態、アイドル状態、ウェイト状態、ALSに移行します。
これらの状態変化は低消費電力化に寄与します。

※詳しくはデータシート『figure8:』の『Test condition』を参照してください。

3.センサーから照度データを取得

#データ読み込み
uv = i2c.read_i2c_block_data(dev_addr, 0x80|0x20|0x14, 0x04)

取得は read_i2c_block_data(adr, reg, size)関数を使用します。

第1引数 adr:I2C通信のアドレス
第2引数 reg:先頭のレジスタ(測定データの記憶場所)
第3引数 size:データのサイズ

i2c.read_i2c_block_data(dev_addr, 0x80|0x20|0x14, 0x04)

0x14は、読み込み開始するアドレス(Ch0データのLSB)です。
0x04は、読み込むバイト数です。

4.データを物理量に変換し画面に表示

#データ変換
ch0 = uv[1] << 8 | uv[0]
ch1 = uv[3] << 8 | uv[2]

ch0 = uv[1] << 8 | uv[0]
読み込んだデータは8bitの入れ物2つ入っているので、16bitにします。

16bitデータ
#物理量(UV照度)に変換
ch0 = ch0 / 19.0
ch1 = ch1 / 10.8

Ch0を19.0で割り、Ch1を10.8で割って物理量に変換しています。

Ch0 Ee = 263.9μW/cm2 ADC count value = 5000 count
Ch1 Ee = 263.9μW/cm2 ADC count value = 2850 count

照度 1 μW/cm2 辺りのADC countは、以下の様に計算できます。

Ch0 5000 / 263.9 ≒ 19 count / μW/cm2
Ch1 2850 / 263.9 ≒ 10.8 count / μW/cm2

※ADC count valueの50002850については、データシート『figure8:』の表の『ADC count value』を参照してください。

#表示
print('ch0: ' + str(ch0))
print('ch1: ' + str(ch1))

print(‘ch0: ‘ + str(ch0))
可視光および赤外光のCh0と赤外光のCh1のUV照度を画面に表示します。

5.3.~4.を繰り返します

#繰り返し
while True:

while True:
Stopボタンが押されるまで繰り返します。

※この『while True:』は、14行目のwhile文です。

プログラムの実行結果

プログラムを実行します。

①Runボタンを押します
②可視光と赤外光(Ch0)、赤外光(Ch1)のUV照度データを1秒間隔で画面に表示します
③Stopボタンを押すとプログラムは終了します

手を近づけてセンサーを暗くすると値が小さくなることで、動作確認できます。

PythonのRunボタンとStopボタン
TSL25721のプログラムの実行結果

以上、TSL25721からI2C通信でUV照度データを読み込んで画面に表示するサンプルでした。

まとめ

照度データの確認は、手を近づけて値が小さくなったり、遠ざけてその逆であったりの確認を行いました。現時点では照度を校正する機器が無いので、読み込んだデータがどの程度の精度でどの程度のリニアリティがあるのか分からない状態です。

TSL25721は、低消費電力化のためにスリープと電源ONの状態だけでなく、アイドルやウェイトなどいろいろあります。データシートにはこの状態を示した状態遷移や移行方法などの記載があります。

プログラミングやソフトウェアの記事です。

コメント