スクラッチくらぶ上級編ーmicro:bit_3

★★★★★ ★★★★★ ★★★★★

BBC micro:bit は小さなコンピュータデバイスです。このデバイスで使える言語に、よく知られた Python があります。BBC micro:bit で動作する Python は MicroPython というものです。

ここではmicro:bit の持つ豊富な機能と、高度なプログラミング言語 MicroPython の組み合わせについて紹介します。

このページは、BBC micro:bit MicroPython ドキュメンテーションを参照しています。 https://microbit-micropython.readthedocs.io/ja/latest/

★★★★★ ★★★★★ ★★★★★

micro:bit(マイクロビット)は、イギリスの放送局BBCで開発された教育用のマイコンボードです。※micro:bitは、micro:bit教育財団の登録商標です。

★★★★★ ★★★★★ ★★★★★

1.チュートリアル

Hello, World!イメージボタン入出力
ミュージックランダム動きの検知ジェスチャー
方角の検知ストレージ音声ネットワーク
無線通信

チュートリアルのページへ飛ぶ

★★★★★ ★★★★★ ★★★★★

2.APIリファレンス

Microbit モジュール加速度センサーオーディオBluetooth
ボタンコンパスディスプレイローカル永続ファイルシステム
I2CイメージミュージックNeoPixel
入出力端子無線通信乱数生成音声
SPIUARTutime

APIリファレンスのトップページへ飛ぶ

★★★★★ ★★★★★ ★★★★★

2.micro:bit Micropython API(APIリファレンス)

■ミュージック

ミュージックのための music モジュールが用意されています。スピーカーをボードに接続すれば、簡単な曲を演奏することができます。デフォルトで、music モジュールはスピーカーが端子 0 を介して接続されることを期待しています

このモジュールにアクセスするには、以下が必要です。

import music

ミュージック表記

NOTE[octave][:duration]

たとえば A1:4 は音名(NOTE) “A”、オクターブ(octave) 1、長さ(duration)が 4 ティックであることを意味します(ティックは後述するテンポ設定機能で定義された任意の長さです)。音の名前に R が指定されている場合は、休符(無音)として扱われます。

臨時記号(フラットとシャープ)は b (フラット – 小文字の b)と # (シャープ – ハッシュ記号)で示されます。たとえば Ab は A フラットであり C# は C シャープです。

オクターブ octave と長さ duration パラメータは、再び指定されるまで、後続の音に引き継がれます。デフォルトの状態は octave = 4 (ミドルの C を含む)と duration = 4 (後述のテンポ設定でデフォルトで与えられている4分音符)です。

たとえば、4 ティックが4分音符の場合、以下のリストは、4分音符、8分音符、8分音符、4分音符ベースのアルペジオです。

['c1:4', 'e:2', 'g', 'c2:4']

1 オクターブの定義と範囲は、 このページの科学的な音程表記についての表 にしたがいます。たとえば、ミドル “C” は 'c4' で、コンサート “A” (440)は 'a4' です。オクターブは音 “C” で始まります。

—————————————————————————————————-

関数

 music.set_tempo(ticks=4, bpm=120) 

再生するためのおおよそのテンポを設定します。

(整数で表される)ティック数 ticks が1ビートを構成します。各ビートは、1分あたりの特定の周波数で再生されます(これはよく知られた BPM – beats per minute – を整数で指定します)。

推奨されるデフォルト値では、次のような便利な動作が可能です。

①.music.set_tempo() – テンポをデフォルト値の ticks = 4, bpm = 120 にリセットする

②.music.set_tempo(ticks=8) – ビートの「定義」を変更する

③.music.set_tempo(bpm=180) – テンポを変えるだけです

ミリ秒単位でティックの長さは非常に簡単な計算で求まります 60000/bpm/ticks_per_beat 。デフォルト値は 60000/120/4 = 125ミリ秒 または 1 beat = 500ミリ秒 となります。

—————————————————————————————————-

 music.get_tempo() 

現在のテンポを整数のタプル (ticks, bpm) として取得します。

—————————————————————————————————-

 music.play(music, pin=microbit.pin0, wait=True, loop=False) 

先に説明したミュージック表記を含んだ music を演奏します。

music が文字列ならば 'c1:4' のような単一の音であることが期待されます。

music が音のリストとして指定されている場合、それらは順番に演奏されてメロディを演奏します。

どちらの場合も、duration octave の値は、音楽が再生される前にデフォルトにリセットされます。

出力端子を指定するためのオプションの引数を使用して、出力端子のデフォルト microbit.pin0 を変更できます。

wait True の場合、この関数はブロックします。

loop True の場合、曲は stop (後述)が呼ばれるか、ブロックが解除されるまで繰り返し演奏されます。

—————————————————————————————————-

 music.pitch(frequency, duration=-1, pin=microbit.pin0, wait=True) 

指定されたミリ秒間の整数周波数でピッチを再生します。たとえば、周波数を 440 に設定し、長さを 1000 に設定すると、標準のコンサート A が1秒間聞こえます。

一度に一つの端子で一つのピッチしか再生できないことに注意してください。

wait True の場合、この関数はブロックします。

duration が負の場合、ブロックが解除されるか、バックグラウンドで新しい周波数が設定されるか、stop (後述)が呼び出されるまで、ピッチが連続して再生されます。

—————————————————————————————————-

 music.stop(pin=microbit.pin0) 

指定された端子のすべての音楽再生を停止します。たとえば music.stop(pin1) のように使います。music.stop() のように端子を指定しない場合は pin0 が指定されたものとします。

—————————————————————————————————-

 music.reset()  

次のように属性の状態をリセットします。

①.ticks = 4 

②.bpm = 120 

③.duration = 4 

④.octave = 4 

—————————————————————————————————-

内蔵メロディ

教育と娯楽の目的のために、このモジュールには、Python のリストとして表現されるいくつかの楽曲が含まれています。これらは次のように使用できます。

※1つの例です。

>>> import music
>>> music.play(music.NYAN)

NYAN – Nyan Cat テーマ (http://www.nyan.cat/)。作曲家は不明です。これは educational porpoises にとって(彼らがニューヨークで言っているように)公正な利用です。

サンプルコード

"""
    music.py
    ~~~~~~~~

    microPython の music モジュールを使って簡単な曲を演奏します。
    このサンプルでは、P0 と GND の端子にスピーカー/ブザー/ヘッドホンを繋ぐ必要があります。
"""
from microbit import *
import music

# C (4分の4拍子)でプレリュードを演奏。
notes = [
    'c4:1', 'e', 'g', 'c5', 'e5', 'g4', 'c5', 'e5', 'c4', 'e', 'g', 'c5', 'e5', 'g4', 'c5', 'e5',
    'c4', 'd', 'a', 'd5', 'f5', 'a4', 'd5', 'f5', 'c4', 'd', 'a', 'd5', 'f5', 'a4', 'd5', 'f5',
    'b3', 'd4', 'g', 'd5', 'f5', 'g4', 'd5', 'f5', 'b3', 'd4', 'g', 'd5', 'f5', 'g4', 'd5', 'f5',
    'c4', 'e', 'g', 'c5', 'e5', 'g4', 'c5', 'e5', 'c4', 'e', 'g', 'c5', 'e5', 'g4', 'c5', 'e5',
    'c4', 'e', 'a', 'e5', 'a5', 'a4', 'e5', 'a5', 'c4', 'e', 'a', 'e5', 'a5', 'a4', 'e5', 'a5',
    'c4', 'd', 'f#', 'a', 'd5', 'f#4', 'a', 'd5', 'c4', 'd', 'f#', 'a', 'd5', 'f#4', 'a', 'd5',
    'b3', 'd4', 'g', 'd5', 'g5', 'g4', 'd5', 'g5', 'b3', 'd4', 'g', 'd5', 'g5', 'g4', 'd5', 'g5',
    'b3', 'c4', 'e', 'g', 'c5', 'e4', 'g', 'c5', 'b3', 'c4', 'e', 'g', 'c5', 'e4', 'g', 'c5',
    'a3', 'c4', 'e', 'g', 'c5', 'e4', 'g', 'c5', 'a3', 'c4', 'e', 'g', 'c5', 'e4', 'g', 'c5',
    'd3', 'a', 'd4', 'f#', 'c5', 'd4', 'f#', 'c5', 'd3', 'a', 'd4', 'f#', 'c5', 'd4', 'f#', 'c5',
    'g3', 'b', 'd4', 'g', 'b', 'd', 'g', 'b', 'g3', 'b3', 'd4', 'g', 'b', 'd', 'g', 'b'
]

music.play(notes)

★★★★★ ★★★★★ ★★★★★

■NeoPixel

neopixel モジュールを使用すると、個別にアドレス可能な RGB LED ボードである NeoPixel (WS2812) を micro:bit で使えます。この neopixel モジュールを使う場合は、以下のモジュールをインポートする必要があります。

import neopixel

クラス

 class neopixel.NeoPixel(pin, n) 

端子pin を介して制御する n 個の neopixel LED を持つボードを初期化します。各ピクセルは、位置(0から始まる)によってアドレス指定されます。ネオピクセルにはタプルとして0-255 の RGB (赤, 緑, 青) 値が与えられます。たとえば (255,255,255) は白です。

 clear() 
 すべてのピクセルをクリアします。

—————————————————————————————————-

 show() 
 ピクセルを表示します。更新が表示するには、これを呼び出す必要があります。

—————————————————————————————————-

演算子

色を書き込んでも表示は更新されません(表示するには show() を呼び出します。

np[0] = (255, 0, 128)  # 最初の素子
np[-1] = (0, 255, 0)  # 最後の素子
np.show()  # 更新された値が表示されます

NeoPixel の使い方

NeoPixel とのやりとりは、それがタプルのリストであるかのように行えます。各タプルは、特定のピクセルの色の RGB (赤, 緑, 青) の組み合わせを表します。RGB値の範囲は 0 から 255 までです。

たとえば、次のように pin0 に接続された 8 ピクセルの NeoPixel ボードを初期化します。

import neopixel
np = neopixel.NeoPixel(pin0, 8)

それらピクセルを(Python のリストのように)インデックス付けして設定します。たとえば、最初のピクセルを最大照度の赤に設定するには次のようにします。

np[0] = (255, 0, 0)

最後のピクセルを紫色にするには次のようにします。

np[-1] = (255, 0, 255)

ピクセルの現在のカラー値を得るには、インデックス付けして参照します。たとえば、最初のピクセルの RGB 値を表示するには次のようにします。

print(np[0])

最後に、新しい色データを NeoPixel ボードの表示に反映するには、.show()関数を使います。

np.show()

何も起こらない場合、おそらくあなたはこの最終ステップを忘れてしまっているのです。

【注釈】

NeoPixel ボードで何か変化が見られない場合、少なくともアップデートしたものが表示されていなければ、show() を確認してください。

サンプルコード

"""
    neopixel_random.py

    LED ボードにランダムな色を繰り返し表示します。
    このサンプルでは、8 Neopixel のボード(WS2812)を pin0 に接続する必要があります。

"""
from microbit import *
import neopixel
from random import randint

# 8 ピクセルの Neopixel ボードを pin0 に接続されていることを設定
np = neopixel.NeoPixel(pin0, 8)

while True:
    # ボードにある各 LED について繰り返し

    for pixel_id in range(0, len(np)):
        red = randint(0, 60)
        green = randint(0, 60)
        blue = randint(0, 60)

        # 現在の LED を 0〜60 のランダムな赤、緑、青の値に設定
        np[pixel_id] = (red, green, blue)

        # Neopixel ボード上の現在のピクセルデータを表示
        np.show()
        sleep(100)

★★★★★ ★★★★★ ★★★★★

■入出力端子

コネクタの端子に、デジタルおよびアナログの入出力機能を提供します。一部の端子は LED マトリクスとボタンを駆動する I/O に内部接続されています。

各端子は microbit モジュールで直接オブジェクトとして提供されます。これにより API が比較的フラットに保たれ、利用が非常に簡単になります。

これらの端子はそれぞれ MicroBitPin クラスのインスタンスであり、次のAPIを提供します。

# 値 value を 0, 1, False, True のいずれかにできます。
pin.write_digital(value)
# 1 か 0 を返します。
pin.read_digital()
# value は 0 から 1023 の範囲の値です。
pin.write_analog(value)
# 0 から 1023 の範囲の整数値を返します。
pin.read_analog()
# 端子の PWM 出力周期をミリ秒単位で設定します。
# (https://ja.wikipedia.org/wiki/パルス幅変調 を参照)
pin.set_analog_period(int)
# 端子の PWM 出力周期をマイクロ秒単位で設定します。
# (https://ja.wikipedia.org/wiki/パルス幅変調 を参照)
pin.set_analog_period_microseconds(int)
# 端子に触れているかをブール値で返します。
pin.is_touched()

★★★★★ ★★★★★ ★★★★★

下図は、例として Yahboom 製の拡張ボード (YBoard) です。

★★★★★ ★★★★★ ★★★★★

属性

端子はボードに接続された外部デバイスと通信するための手段。使用できる端子は 19 あります。番号 0-16 と 19-20 を利用できます。端子 17 と 18 は利用できません。

たとえば、下記のMicroPythonスクリプトは端子 0 のデジタル読み取り、値に応じてマイクロビットの表示を変更します。

from microbit import *


while True:
    if pin0.read_digital():
        display.show(Image.HAPPY)
    else:
        display.show(Image.SAD)

★★★★★ ★★★★★ ★★★★★

各端子の機能

_images/pinout.png

★★★★★ ★★★★★ ★★★★★

これらの端子は、micro:bit モジュールの属性として利用できます。microbit.pin0-microbit.pin20

小さなピンはmicrobitのコンポーネントと共有されています。

ピン0
PAD 0
ANALOG IN
アナログ
アナログ‐デジタルコンバータ(ADC)付きGPIO(汎用デジタル入出力)  
ピン1
PAD 1
ANALOG IN
アナログ
ADC付きGPIO  
ピン2
PAD 2
ANALOG IN
アナログ
ADC付きGPIO  
ピン3
ANALOG IN・
LED Col1
アナログ/デジタル
GPIOはLEDスクリーンのLED Col1と共有されます。LEDを使っていない時、ADCとデジタルI/Oに使用することができます。 
ピン4
ANALOG IN ・
LED Col2
アナログ/デジタル
GPIOはLEDスクリーンのLED Col2と共有されます。LEDを使っていない時、ADCデジタルI/Oに使用することができます。 
ピン5
BOTTON A
デジタル
GPIOはボタンAと共有される。これによってボタンAのクリックを外部からトリガーまたは検出することができる。このピンはプルアップ抵抗を備えています。つまりデフォルトは3Vです。ボタンAを外部ボタンに置き換えるときには、外部ボタンの一端をピン5に接続して、他端をGNDに接続します。ボタンを押すと、ピン5の電圧が0にプルダウンされて、ボタンクリックイベントが作成されます。
ピン6
LED Col9
デジタル
GPIOはLEDスクリーンのLED Col9と共有します。LEDを使っていないときにデジタルI/Oに使用することができます。 
ピン7
LED Col8
デジタル
GPIOはLEDスクリーンのLED Col9と共有します。LEDを使っていない時にデジタルi/Oに使用することができます。 
ピン8
デジタル
デジタル信号を送信および検出するための専用GPIOです。 
ピン9
LED Col7
デジタル
GPIOはLEDスクリーンのLED Col7と共有されます。LED使っていない時に使用することができます。 
ピン10
LED Col10
アナログ/デジタル
ピン10:GPIOはLEDスクリーンのLED Col3と共有します。LEDを使っていない時にADCとデジタルI/Oに使用することができます。 
ピン11
BOTTON B
デジタル
GPIOはボタンBと共有されます。これによって、外部でボタンBのクリックをトリガーまたは検出ことができます。 
ピン12
Reserved:accessibillity
デジタル
デジタル信号を送信及びセンシングするための専用GPIO。  
ピン13
SPI SCK
デジタル
3線シリアルペリフェラルインターフェイス(SPI)バスノシリアルロック(SCK)信号に従来使用されていたGPIO。  
ピン14
SPI MISO
デジタル
SPIバスのMISO(Master In Slave Out)信号に従来使用されていたGPIO。  
ピン15
SPI MOSI
デジタル
SPIバスのMOSI(Master Out Slave)信号用に従来使用されていたGPIO。  
ピン16
デジタル
専用GPIO(従来はSPIのチップセレクト機能にも使用されていた。) 
ピン17・ピン18
+3V3
この2つのピンは大きなピン「3V」と同じように3V電源が接続されています。  
ピン19・ピン20
I2c1scl
デジタル
I2Cバス通信プロトコルのクロック信号(SCL)=ピン19 と、データライン(SDA)=ピン20 が実装されています。I2Cでは複数のデバイスを同じバスに接続してCPUとの間でメッセージの送受信をすることができます。このピンは、microbit内部の加速度センサーとコンパスはi2cに接続されています。 
ピン21・ピン22
GND
この2つのピンはGNDに配線されています。GND以外の機能はありません。 

※小さなピンを使うときは、microbit用のEdge Connector(エッジコネクタ)などを利用すると作業がやりやすくなります。

★★★★★ ★★★★★ ★★★★★

PWM (Pulse-Width Modulation)

ボードの端子は、オーディオアンプが行っているような電圧の変調によるアナログ信号を出力できません。端子は、3.3V のフル出力をイネーブルするか、または 0V にプルダウンするだけです。しかし、LED の明るさや電気モーターの速度を制御することは、その電圧を非常に高速にオン/オフし、オン時間とオフ時間を制御することによっても可能です。この技術はパルス幅変調(PWM)と呼ばれ、write_analog メソッドで行います。

_images/pwm.png

上には 3 つの異なる PWM 信号の図があります。それらはすべて同じ周期(つまり周波数)を持ちますが、時間幅周期が異なります。

★★★★★ ★★★★★ ★★★★★

最初のものは write_analog(511) で生成されたものであり、正確に 50% の時間幅を持ちます。パワーは時間の半分がオン、時間の半分がオフです。その結果、この信号の全エネルギーは、3.3V の代わりに 1.65V の場合と同じです。

第2の信号は 25% の時間幅周期を有し、write_analog(255) を用いて生成できます。この端子に 0.825V が出力されている場合と同様の効果があります。

第3の信号は 75% の時間幅周期を有し、code>write_analog(767) を用いて生成できます。第2の信号の3倍のエネルギーを有し、第1端子に 2.475V を出力することと同等です。

これは、大きな慣性を持っているモーターなどのデバイスや、人間の目ではわからないほど速く点滅している LED などのデバイスではうまくいきますが、音の発生ではあまりよい結果になりません。このボードは矩形波の音だけを生成可能です。

★★★★★ ★★★★★ ★★★★★

クラス

3種類の端子があり、利用法も異なります。それらは、以下に列挙されるクラスによって表されます。これらクラスは階層を形成しています。各クラスは前のクラスのすべての機能を持ち、独自のものを追加しています。

【注釈】

これらのクラスは実際には利用できません。新しいクラスのインスタンスを作成することはできません。ボード上の物理的な端子を表す、すでに提供されているインスタンスのみを使用できます。

 class microbit.MicroBitDigitalPin 
 read_digital() 
 端子がハイの場合は 1 を返し、ローの場合は 0 を返します。

—————————————————————————————————-

 write_digital(value) 
  value が 1 の場合はハイに設定し、0 の場合はローに設定します。

—————————————————————————————————-

 set_pull(value) 
 プル状態を次の3つの値どれかに設定します。pin.PULL_UP , pin.PULL_DOWN , pin.NO_PULL (ここで pin は端子のインスタンスのことです)。既定のプル状態については後述します。

—————————————————————————————————-

 get_pull() 
 現在の端子のプル設定を返します。次の3つのいずれかの値が返ります。NO_PULL , PULL_DOWN , PULL_UP 。これらの値は set_pull() メソッドで設定されるか、端子モードで必要なときに自動的に設定されます。

—————————————————————————————————-

 get_mode() 
 端子モードを返します。
デジタル値の書き込みやアナログ値の読み出しなど、端子を特定の機能で使うと端子モードが変化します。
端子は次のいずれかのモードを持つことができます。
MODE_WRITE_ANALOG , MODE_READ_DIGITAL ,
MODE_WRITE_DIGITAL , MODE_DISPLAY ,
MODE_BUTTON , MODE_MUSIC ,
MODE_AUDIO_PLAY , MODE_TOUCH ,
MODE_I2C , MODE_SPI

—————————————————————————————————-

 class microbit.MicroBitAnalogDigitalPin 
 read_analog() 
 端子の電圧を読み取り、0 (0V の意味)から 1023 (3.3V の意味)までの間の整数として返します。

—————————————————————————————————-

 write_analog(value) 
 PWM 信号を端子に出力します。時間幅周期は供給電圧 value に比例します。value には 0 (時間幅周期 0%)から 1023 (時間幅周期 100%)までの整数または浮動小数点数を指定できます。

—————————————————————————————————-

 set_analog_period(period) 
 出力される PWM 信号の周期を period にミリ秒単位で設定します。有効な最小値は 1ms です。

—————————————————————————————————-

 set_analog_period_microseconds(period) 
 出力される PWM 信号の周期を period  にマイクロ秒単位で設定します。有効な最小値は 256μs です。

—————————————————————————————————-

 class microbit.MicroBitAnalogDigitalPin 
 read_analog() 
 端子の電圧を読み取り、0 (0V の意味)から 1023 (3.3V の意味)までの間の整数として返します。

—————————————————————————————————-

 class microbit.MicroBitTouchPin 
 is_touched() 
 端子を指で触れている場合は True 、そうでない場合は False を返します。
このテストは、端子と接地(GND)の間にどれだけの抵抗があるかを測定することによって行われます。抵抗が少ないと True の判定を返します。指での検出を確実にするには、体の別の部分、たとえばもう片方の手で GND 端子に触れる必要があるかもしれません。

端子のプルモードは、端子が入力モードに変わると自動的に構成されます。入力モードは read_analog / read_digital / is_touched を呼び出すと自動で設定されます。これらのメソッドで設定されるデフォルトのプルモードは、それぞれ NO_PULL, PULL_DOWN, PULL_UP です。set_pull を呼び出すと、read_digital モードにある端子を指定のプルモードに設定します。

【注釈】

タッチセンスが機能するために、micro:bit は端子 0, 1, 2 にのみ外付けの弱い(10M)プルアップを装備しています。

ボタンAとボタンBが機能するように、端子 5 と 11 にも外付け(10k)プルアップを装備しています。

GPIO 端子はディスプレイにも使われています。GPIO 端子のうちの6つはエッジコネクタ 3, 4, 6, 7, 9, 10 に配線されています。別の目的でこれらの端子を使いたいときには ディスプレイを無効 にする必要があります。

エッジコネクタのデータシート を参照してください。

★★★★★ ★★★★★ ★★★★★

■無線通信

radio モジュールにより、デバイスは単純な無線ネットワークを介して連携することができます。

①. ブロードキャストメッセージは設定可能な長さ(最大251バイト)です。
②. メッセージはブロードキャストされ、あらかじめ選択されたチャネル(0〜83 の番号が付けられています)で受信されます
③. メッセージはアドレスとグループでフィルタリングされます。
④. スループットのレートは、3つの事前設定のいずれかになります。
⑤. 入ってくるメッセージについて詳細を得るには receive_full を使います: 得られる情報には、データ、受信信号強度、メッセージを受信したタイムスタンプ(ミリ秒単位)があります。

import radio

—————————————————————————————————-

定数

 radio.RATE_250KBIT  

256 Kbit/秒のスループットを示すために使われる定数です。

—————————————————————————————————-

 radio.RATE_1MBIT  

1 MBit/秒のスループットを示すために使われる定数です。

—————————————————————————————————-

 radio.RATE_2MBIT  

2 MBit/秒のスループットを示すために使われる定数です。

—————————————————————————————————-

関数

 radio.on()  

無線通信をオンにします。無線通信は電力を消費し、他で必要となるかもしれないメモリも占有するため、明示的に呼び出す必要があります。

—————————————————————————————————-

 radio.off()  

無線通信をオフにして、電力とメモリを節約します。

—————————————————————————————————-

 radio.config(**kwargs)  

無線通信に関連するさまざまなキーワードベースの設定を構成します。利用可能な設定とその適切なデフォルト値を以下に示します。

length (デフォルト=32)は、無線を介して送信されるメッセージのバイト単位の最大長を設定します。最大で 251 バイト(254 から S0、長さ、S1 プリアンブルを引いた値)にできます。

queue (デフォルト=3)は、受信メッセージキューに格納できるメッセージの数を指定します。着信メッセージのキューに空きがない場合、着信メッセージは捨てられます。

channel (デフォルト=7)は、無線が同調されている任意の「チャネル」を定義するもので、0 から 83 までの整数値を設定できます。メッセージはこのチャネル経由で送信され、このチャネル経由で受信したメッセージだけが受信メッセージキューに入れられます。各ステップは 1MHz 幅で、2400MHz を基準にしています。

power (デフォルト=6)は、メッセージをブロードキャストするときに使用される信号の強度を示すもので、0 から 7 までの整数値を設定できです。値が高いほど信号は強くなりますが、デバイスが消費する電力が大きくなります。指定の番号は次のリストの dBm (デシベルミリワット)値の位置に変換されます: -30, -20, -16, -12, -8, -4, 0, 4 。

address (デフォルト=0x75626974)は、32 ビットのアドレスとして表される任意の名前であり、ハードウェアレベルで着信パケットをフィルタリングするために使用されます。フィルタリングはユーザーが設定したアドレスと一致するもののみを維持します。他の micro:bit 関連のプラットフォームで使われるデフォルトは、ここで使用されるデフォルト設定です。

group (デフォルト=0)は、8ビットの値(0〜255)であり、 address フィルタしたメッセージで使います。概念的に “address” は自宅/事務所の住所のようなものであり、”group” はその住所のメッセージを受け取る人のようなものです。

data_rate (デフォルト=radio.RATE_1MBIT)は、データスループットが起こる速度を示しています。 radio モジュールに定義されている以下の定数のいずれかになります RATE_250KBIT , RATE_1MBIT , RATE_2MBIT

config を呼び出さない場合は、上記のデフォルトが仮定されます。

—————————————————————————————————-

 radio.reset()  

設定を既定値にリセットします(上記の config 関数のドキュメントに記載されています)。

【注釈】

無線通信がオンになるまで、以下の送受信のメソッドは機能しません。

—————————————————————————————————-

 radio.send_bytes(message)  

バイト列を含むメッセージを送信します。

—————————————————————————————————-

 radio.receive_bytes()  

メッセージキューで次の着信メッセージを受信します。保留中のメッセージがない場合は None を返します。メッセージはバイト列として返されます。

—————————————————————————————————-

 radio.receive_bytes_into(buffer)  

メッセージキューで次の着信メッセージを受信します。メッセージを buffer にコピーし、必要に応じてメッセージの最後を切り取ります。保留中のメッセージがない場合は None を返し、そうでない場合はメッセージの長さを返します(バッファの長さ以上の場合もあります)。

—————————————————————————————————-

 radio.send(message)  

メッセージ文字列を送信します。これは send_bytes(bytes(message, 'utf8')) と同等ですが、 b'x01x00x01' を前に付加します(micro:bit をターゲットとする他のプラットフォームと互換性を持たせるためです)。

—————————————————————————————————-

 radio.receive()  

receive_bytes と同じように動作しますが、送信されてきたものはすべて返します。

現在のところ、これは str(receive_bytes(), 'utf8') と同等ですが、最初の3バイトが b'x01x00x01' であることをチェックします(micro:bit をターゲットとする可能性のある他のプラットフォームと互換性を持たせるため)。文字列に変換する前に、先頭に付加された3バイトを削除します。

文字列への変換が失敗した場合は、ValueError 例外が発生します。

—————————————————————————————————-

 radio.receive_full()  

キューにある次のメッセージを表す3つの値のタプルを返します。キューに保留しているメッセージがない場合には None を返します。

タプルで返す3つの値は次のものです。

①. キューにある次のメッセージのバイト列。

②. RSSI (信号強度): dBm で測った信号の強さ。0 が最も強く、-255 が最も弱い。

③. マイクロ秒単位のタイムスタンプ: メッセージを受信したときの time.ticks_us() が返す値。

details = radio.receive_full()
if details:
    msg, rssi, timestamp = details

この関数は、他の micro:bit デバイスとの三角測量(Triangulation)や三辺測量(Triliteration)を行うために必要な情報を提供するのに便利です。

★★★★★ ★★★★★ ★★★★★

■乱数生成

このモジュールは Python 標準ライブラリの random モジュールをベースにしています。このモジュールはランダムな振舞いを生成する関数を持っています。

import random

関数

 random.getrandbits(n)  

n 乱数ビット数を持つ整数を返します。

—————————————————————————————————-

 random.seed(n)  

乱数ジェネレータを指定の整数 n で初期化します。これは、与えられた開始状態( n )から再現性のある決定論的なランダム性を与えます。

—————————————————————————————————-

 random.randint(a, b)  

a <= N <= b となるような整数の乱数 N を返します。これは randrange(a, b+1) と同等です。

—————————————————————————————————-

 random.randrange(stop)  

0 から stop 未満までの間で無作為に選択された整数を返します。

—————————————————————————————————-

 random.randrange(start, stop)  

range(start, stop) から無作為に選択された整数を返します。

—————————————————————————————————-

 random.randrange(start, stop, step)  

range(start, stop, step) から無作為に選択された要素を返します。

—————————————————————————————————-

 random.choice(seq)  

空でないシーケンス seq からランダムな要素を返します。seq が空の場合は、 IndexError が発生します。

—————————————————————————————————-

 random.random()  

range(0.0, 1.0) から無作為に選択された浮動小数点数を返します。

—————————————————————————————————-

 random.uniform(a, b)  

a <= b の場合に a <= N <= b b < a の場合に b <= N <= a となるような浮動小数点数の乱数 N を返します。

★★★★★ ★★★★★ ★★★★★

■音声

このモジュールで micro:bit に話をさせ、歌わせ、その他の音声のようなサウンドを作るのにスピーカーを以下に示すようにボードに接続するという前提で説明します。

★★★★★ ★★★★★ ★★★★★

音声シンセサイザーは、最大255文字のテキスト入力から約2.5秒分の音量を生成できます。

このモジュールにアクセスするには、以下を行う必要があります。

import speech

関数

 speech.translate(words)  

文字列 words にある英単語の並びについて、発声するのに最適な音素を推測して、文字列として返します。出力は、このテキスト-音素変換テーブル にしたがって生成されます。

この関数は、音素の近似を最初に生成するために使うべきです。この結果を元に手で編集して、精度、屈曲、強調を改善することができます。

—————————————————————————————————-

 speech.pronounce(phonemes, *, pitch=64, speed=72, mouth=128, throat=128)  

文字列 phonemes が表す音素を発声します。音声合成器の出力を細かく制御するために音素を使用する方法の詳細については後述します。オプションの pitch, speed, mouth, throat の設定を上書きして、声の音色(音質)を変更します。

—————————————————————————————————-

 speech.say(words, *, pitch=64, speed=72, mouth=128, throat=128)  

文字列 words にある英単語の並びを発声します。結果は実際の英語の半分程度の精度です。オプションの pitch、speed、mouth、throat の設定を上書きして、声の音色(音質)を変更します。この関数は次の呼び出しを短くしたものです。 speech.pronounce(speech.translate(words))

—————————————————————————————————-

 speech.sing(phonemes, *, pitch=64, speed=72, mouth=128, throat=128)  

文字列 phonemes が表す音素を歌います。音符のピッチと持続時間を変更する方法は後述します。オプションの pitch、speed、mouth、throat の設定を上書きして、声の音色(音質)を変更します。

—————————————————————————————————-

句読点

句読点は、音声の伝達を変更するのに使います。シンセサイザーは、ハイフン、カンマ、フルストップ、疑問符の4つの句読点を認識します。

ハイフン ( - )は音声に短い休止を入れることによって、句を区切ります。

カンマ ( , )はハイフンの約2倍のポーズを挿入することにより、フレーズを区切ります。

終止符 ( . ) と疑問符 ( ? ) の終了文。

終止符はポーズを挿入し、ピッチを落とします。

疑問符もポーズを挿入しますが、ピッチが上がります。これは “are we home yet?” のような yes/no で答えられる質問に適しています”why are we going home?” のようなより複雑な質問では終止符を使ってください。

音色

音色は音の質です。それは、(たとえば) DALEK の声と人間の声の違いです。音色を制御するには、pitch , speed , mouth , throat 引数の数値設定を変更します。

pitch (音程の高低)と speed (音声の速さ)の設定はかなり明白で、一般的に次のカテゴリに分類されます。

pitch:

・0-20 実用的でない
・20-30 非常に高い
・30-40 高い
・40-50 高めのノーマル
・50-70 ノーマル
・70-80 低めのノーマル
・80-90 低い
・90-255 非常に低い

(デフォルトは 64)

speed:

・0-20 実用的でない
・20-40 非常に速い
・40-60 速い
・60-70 早口な会話
・70-75 普通の会話
・75-90 説話
・90-100 遅い
・100-225 非常に遅い

(デフォルトは 72)

mouth と throat の値は説明するのが少し難しく、以下の説明は、各設定の値が変更されたときに生成される音声の聴覚の印象に基づいています。

mouth については、数字が低いほどスピーカーが唇を動かさずに話しているように聞こえます。対照的に、数字が高いほど(最大255)、声が誇張された口の動きで発声されるように聞こえます。

throat については、数が少ないほどスピーカーの響きが緩和されます。対照的に、数字が高いほど、緊張感が増します。

speech.say("I am a little robot",  speed=92, pitch=60, throat=190, mouth=190)
speech.say("I am an elf", speed=72, pitch=64, throat=110, mouth=160)
speech.say("I am a news presenter", speed=82, pitch=72, throat=110, mouth=105)
speech.say("I am an old lady", speed=82, pitch=32, throat=145, mouth=145)
speech.say("I am E.T.", speed=100, pitch=64, throat=150, mouth=200)
speech.say("I am a DALEK - EXTERMINATE", speed=120, pitch=100, throat=100, mouth=200)

歌唱

MicroPython に音素を歌わせることは可能です。

これは音素にピッチ関連の番号を注釈することによって行います。数字が小さいほど、ピッチが高くなります。数字はおおよそ次の図に示すように音符に変換されます。

音素の前にハッシュ記号( # )とピッチ番号をあらかじめ付けておくことにより有効となります。新しい注釈が与えられるまで、ピッチは同じままになります。たとえばを次のようにして MicroPython に音階を歌わせます。

solfa = [
    "#115DOWWWWWW",   # ド
    "#103REYYYYYY",   # レ
    "#94MIYYYYYY",    # ミ
    "#88FAOAOAOAOR",  # ファ
    "#78SOHWWWWW",    # ソ
    "#70LAOAOAOAOR",  # ラ
    "#62TIYYYYYY",    # シ
    "#58DOWWWWWW",    # ド
]
song = ''.join(solfa)
speech.sing(song, speed=100)

特定の音符を歌わせるには、母音や母音の音韻を繰り返します(上記の例を参照)。二重母音に注意してください。これを伸ばすには、それらを構成部品に分解する必要があります。たとえば、 “OY” は “”OHOHIYIYIY” で伸ばすことができます。

サンプルコード

import speech
from microbit import sleep

# say メソッドは英語から音素への変換を試みます。
speech.say("I can sing!")
sleep(1000)
speech.say("Listen to me!")
sleep(1000)

# throat をクリーンにするには音素を使う必要があります。
# pitch と speed を変更することでも適切な効果が得られます。
speech.pronounce("AEAE/HAEMM", pitch=200, speed=100)  # えへん
sleep(1000)

# 歌わせるには各音節ごとに音階の音素が必要です。
solfa = [
    "#115DOWWWWWW",   # ド
    "#103REYYYYYY",   # レ
    "#94MIYYYYYY",    # ミ
    "#88FAOAOAOAOR",  # ファ
    "#78SOHWWWWW",    # ソ
    "#70LAOAOAOAOR",  # ラ
    "#62TIYYYYYY",    # シ
    "#58DOWWWWWW",    # ド
]

# 音階が順に高くなっていくよう歌わせます。
song = ''.join(solfa)
speech.sing(song, speed=100)
# 音節のリストの順番を逆にします。
solfa.reverse()
song = ''.join(solfa)
# 音階が順に低くなっていくよう歌わせます。
speech.sing(song, speed=100)

★★★★★ ★★★★★ ★★★★★

■SPI

spi モジュールを使用すると、シリアルペリフェラルインターフェイス(SPI)バスを使用して、ボードに接続されたデバイスと通信できます。SPI はいわゆる、単一マスターでのマスター/スレーブアーキテクチャを使用します。SPI は3つの信号の接続を指定する必要があります。

・SCLK : シリアルクロック(マスターから出力)
・MOSI : マスター出力、スレーブ入力(マスターから出力)
・MISO: マスター入力、スレーブ出力(スレーブから出力)

—————————————————————————————————-

関数

 microbit.spi.init(baudrate=1000000, bits=8, mode=0, sclk=pin13, mosi=pin15, miso=pin14)  

指定の端子 pin と指定のパラメータで SPI 通信を初期化します。正しい通信のためには、両方の通信デバイスでパラメータが同じでなければならないことに注意してください。

baudrate は通信速度を定義します。

bits は送信するバイト列のサイズを定義します。現在のところは bits=8 だけをサポートしています。

mode は、以下の規則にしたがってクロックの極性と位相の組み合わせを決定します。極性は上位ビット、極性は下位ビットになります。

SPI モード極性 (CPOL)位相 (CPHA)
000
101
210
311

極性(CPOL)が 0 の場合、クロックがアイドル時には論理値 0、アクティブ時にはハイ(論理値 1)になることを意味します。極性が 1 の場合、クロックがアイドル時には論理値 1、アクティブ時にはロー(論理値 0)になることを意味します。位相(CPHA)0 の場合はデータがクロックのリーディングエッジでサンプリングされ、1 の場合はトレーリングエッジでサンプリングされることを意味します(エッジについては https://en.wikipedia.org/wiki/Signal_edge を参照)。

sclk , mosi , miso 引数には、信号のそれぞれのタイプに使う端子を指定します。

—————————————————————————————————-

 spi.read(nbytes)  

最大 nbytes を読み込みます。読み込んだものを返します。

—————————————————————————————————-

 spi.write(buffer)  

バイト列の buffer をバスに書き出します。

—————————————————————————————————-

 spi.write_readinto(out, in)  

out バッファをバスに書き出し、応答を in バッファに読み込みます。2つのバッファーの長さは同じでなければなりません。2つのバッファは同じオブジェクトでもかまいません。

★★★★★ ★★★★★ ★★★★★

■UART

I/O 端子に接続されたシリアルデバイスとの通信には uart を使います。

# ボーレート 9600 で(端子 0 [TX] と 1 [RX] を使う)通信をセットアップします。
uart.init()
# 読込みを待っている文字を受信しているかにより True または False を
# 返します。
uart.any()
# 受信している文字を n だけ読んで返します。
uart.read(n)
# 受信している文字を可能なだけ(読んで)返します。
uart.read()
# 改行文字に達するまでのすべての文字を(読んで)返します。
uart.readline()
# 指定のバッファにバイト列を読み込みます。
uart.readinto(buffer)
# 接続したデバイスにバッファのバイト列を書き出します。
uart.write(buffer)

—————————————————————————————————-

uart モジュールを使用すると、シリアルインタフェースを使用してボードに接続されたデバイスと通信できます。

関数

 microbit.uart.init(baudrate=9600, bits=8, parity=None, stop=1, *, tx=None, rx=None)  

指定の tx rx 端子と指定のパラメータでシリアル通信を初期化します。正しい通信のためには、両方の通信デバイスでパラメータが同じでなければならないことに注意してください。

baudrate は通信速度を定義します。一般的なボーレートは次のとおりです。

・9600
・14400
・19200
・28800
・38400
・57600
・115200

bits は送信するバイト列のサイズを定義します。現在のところは bits=8 だけをサポートしています。parity パラメータはパリティのチェック方法を定義するもので、None , microbit.uart.ODD , microbit.uart.EVEN を指定できます。stop パラメータは、ストップビットの数を知らせるもので、このボードでは 1 にする必要があります。

tx rx を指定しない場合、内部の USB-UART TX/RX 端子を使用して micro:bit” の USB シリアルコンバータに接続し、UART を PC に接続します。望みの端子オブジェクトを tx rx パラメータに渡すことにより、他の端子を使うように指定できます。

【注釈】

デバイスを接続するときは、ワイヤを “交差させる” ことを確認してください。ボード上の TX 端子はデバイスの RX 端子と、RX 端子はデバイスの TX 端子と接続する必要があります。また、両方のデバイスのグランドピンが接続されていることを確認してください。

—————————————————————————————————-

 uart.any()  

なにか待っているデータがあれば True を返し、さもなければ False を返します。

—————————————————————————————————-

 uart.read([nbytes])  

バイト列を読み込みます。nbytes が指定されていれば、そのバイト数まで読み込みます。指定されていなければ、できるだけ多く読み込みます。

戻り値: バイト列オブジェクト、タイムアウトが起きれば None

bytes オブジェクトには一連のバイトが含まれます。ASCII 文字は1バイトに収めることができるので、このタイプのオブジェクトはしばしば単純なテキストを表現するために使われ、それをそのまま操作する方法を提供します。たちえば print() 関数を使ってテキストを表示できます。

このオブジェクトを文字列オブジェクトに変換することもできます。非 ASCII 文字が存在する場合は、エンコードを指定できます

msg_bytes = uart.read()
msg_str = str(msg, 'UTF-8')

【注釈】

すべての UART 読込みのタイムアウトはボーレートに依存していて、Pythonからは変更できません。タイムアウト値は次の式でミリ秒単位で決まります。 microbit_uart_timeout_char = 13000 / baudrate + 1

【注釈】

内部 UART RX バッファは 64 バイトなので、バッファがいっぱいになる前にデータを読み込んでください。さもないとデータが失われることになります。

—————————————————————————————————-

 uart.readall()  

不要です。 uart.read() を引数なしで使えば、できるだけ多くのデータを読み込みます。

—————————————————————————————————-

 uart.readinto(buf[, nbytes])  

buf にバイト列を読み込みます。nbytes が指定されていれば、そのバイト数まで読み込みます。さもなければ len(buf) のバイト数まで読み込みます。

戻り値: 読み込んで buf に格納したバイト数。タイムアウト時は None

—————————————————————————————————-

 uart.readline()  

1行、すなわち改行文字まで読み込みます。

戻り値: 読み込んだ行。タイムアウト時は None 。返すバイト列に改行文字は含まれます。

—————————————————————————————————-

 uart.write(buf)  
uart.write('hello world')
uart.write(b'hello world')
uart.write(bytes([1, 2, 3]))

戻り値: 書き出したバイト数。タイムアウト時は None

★★★★★ ★★★★★ ★★★★★

■utime

utime モジュールには、現在の時間の取得、時間隔を測定、遅延についての関数があります。

【注釈】

utime モジュールは、標準の Python の time モジュールの MicroPython 版です。 import utime でも import time でもインポートできますが、モジュールは同じものです。

関数

 utime.sleep(seconds)  

指定された秒数の間スリープします。秒より細かい精度で指定したい場合は浮動小数点数を使うか、utime.sleep_ms() utime.sleep_us() 関数を使ってください。

—————————————————————————————————-

 utime.sleep_ms(ms)  

指定のミリ秒間だけ遅延します。ミリ秒の指定は 0 以上の整数である必要があります。

—————————————————————————————————-

 utime.sleep_us(us)  

指定のマイクロ秒間だけ遅延します。マイクロ秒の指定は 0 以上の整数である必要があります。

—————————————————————————————————-

 utime.ticks_ms()  

呼出し時点での稼働時間をミリ秒単位で返します。稼働時間は最大値に達するとラップアラウンドします(一周して最低値に戻ります)。

—————————————————————————————————-

 utime.ticks_us()  

上記の utime.ticks_ms() と同じですが、マイクロ秒単位となります。

—————————————————————————————————-

 utime.ticks_add(ticks, delta)  

与えた数をティック値からのオフセットとして加算した値を返します。引数の値は正でも負でもかまいません。この関数は、ティック値のモジュール算術定義にしたがい、与えた ticks 値とその前後の delta ティックからティック値を算出します。

—————————————————————————————————-

サンプルコード

# 100ms 前のティック値を調べます
print(ticks_add(time.ticks_ms(), -100))

# 操作やテストのためのデッドラインを算出します
deadline = ticks_add(time.ticks_ms(), 200)
while ticks_diff(deadline, time.ticks_ms()) > 0:
    do_a_little_of_something()

# このポートの TICKS_MAX を調べます
print(ticks_add(0, -1))

—————————————————————————————————-

 utime.ticks_diff(ticks1, ticks2)  

utime.ticks_ms() ticks_us() 関数の戻り値(ラップアラウンドである可能性のある符号付きの値)の間のティック値の差を計算します。

引数の順序は減算演算子と同じで、ticks_diff(ticks1, ticks2) ticks1 - ticks2 と同じ意味を持ちます。

utime.ticks_diff() は、さまざまな使用パターンに対応するように設計されています。

※タイムアウトのポーリング – この場合、イベントの順序は既知であり、次のように utime.ticks_diff() の正の結果のみを処理します。

※イベントのスケジューリング – この場合、イベントが期限切れになると utime.ticks_diff() の結果が負になります。

★★★★★ ★★★★★ ★★★★★

チュートリアルのページへ飛ぶ

APIリファレンスのトップページへ飛ぶ

★★★★★ ★★★★★ ★★★★★