今回はarduinoの中でも比較的新しいarduino nano everyのお話です。
このarduino nano everyですが、当然のことながらarduinoIDEを使って開発可能です。
例えばどこかの出力ピンをONにして、接続先のLEDをチカチカさせてみたり。
ただ、複数のGPIOピンを同時に
HIGHにするって難しいですよね?
同時です。
二行に分けてdigitalWriteしたら厳密には同時ではなくなります。
そんな時どうしたらいいのかを解説していきます。
AVRのレジスタが必要になりますから、
この記事も読んでおいたほうがいいです。
↓↓↓↓
それでは張り切っていきましょう!
Youtubeチャンネルにさまざまな動画を上げています。
↓↓↓こちらからYoutubeチャンネルにアクセス!! ↓↓↓
本ブログはアフィリエイトを用いた広告を掲載しています。
Arduino nano everyはatmega4809搭載
Arduino nano everyには、atmega4809という
マイコンが搭載されています。
Arduinoといっても、実は搭載されているマイコンが結構バラバラです。
みんな大好きArduino UNOだと328P
マウス操作やキーボード操作ができるArduino pro microやLeonardoは
32U4を搭載しています。
マイコンがバラバラなので当然、マイコン自体に送るコマンドはバラバラです。
ただ、Arduinoというマイコンボードになっているおかげで、
どのマイコンでもdigitalWriteやdigitalReadが使えるというわけです。
今回紹介するのはArduino nano everyの話なので、
atmega4809にコマンドを送っていく形になります。
ほかのマイコンを積んでいるArduinoは同じようにはできませんので注意が必要です。
atmega4809でGPIOの操作をする方法。
さて、atmega4809を直接いじる方法ですが、
実はArduinoの拡張機能でatmega4809を追加しておくと、
そのマイコン用の指令がライブラリとして読み込まれます。
ですから、実はすべてのコマンドを覚える必要はなく、
それっぽく予測変換で表示されますし、
ライブラリに飛んで、どんな関数があるのかなど見ることも可能です。
ただ、この方法はVScodeを使用しないとライブラリに飛ぶことができなかったりして
とても不便ですから、いまのうちにArduinoIDEから、
VSCodeに移行しておくことを強くオススメしておきます。
具体的な方法についてはこちらの記事で紹介していますので、
参考にしてみてください。
用意するものと配線図
前提として、Arduino nano everyに搭載されているLEDを光らせるのが簡単ですが、
今回は…
ちゃんと同時にGPIOがHIGIになっているかオシロスコープで確認しますので、
外部のGPIOピンと接続されているものしか使えません。
D13ピンは出ていますが、他のRX,TXのピンなどは外部に出てきていませんから、
いっそのこと2個のLEDと抵抗を用意して光らせることにしました。
用意するもの:4つ
用意するものはこの4つです。
冒頭でもお話した通り、今回はマイコンに直接指令をだします。
ですから、他のArduinoとは互換性はありません。
Arduino nano everyの互換品はAmazonなどで見つけることは可能ですが、
atmega4809ではなく、atmega4808だったりするので、
ちゃんと純正のArduino nano every を購入しましょう。
↓↓↓↓↓
ちなみに、いつもは互換品しか購入したことがありませんでしたが、
今回初めて純正品のArduinoを購入しました…(いまさら)。
次に抵抗です。手元にあった1kΩの抵抗を使用しますが、
基本何オームでも大丈夫です。ただ、抵抗無しは危険ですのでやめてください。
Arduinoから出せる最大電流値を超えてしまい、最悪Arduinoが壊れます。
必ず抵抗は入れましょう。
次に、LEDです。何色でも構いません。
抵抗とLEDですが、電子工作キットというのが通販サイトで販売されています。
電子部品を取り扱っている店舗が近くにない…
なんて場合には強い味方ですから、
これを機に購入してみるのもアリではないでしょうか?
↓↓↓amazonで電子工作キットを見てみる↓↓↓
LEDや抵抗はバラバラで購入するより、セットになっているほうが安上がりな場合が多いです。
もちろん単品で購入することに反対はしませんが、
今後のことを考えるとセットで1つ持っておいたほうがいいと思います。
ちなみに…模型など小さいものにもつかえるミニチュアLEDなんかもあります。
この記事で紹介していますので、とにかく小さいLEDが欲しい!
という場合は参考にしてみて下さい。
配線図
配線はこんな感じです。
今回使用するGPIOピンはこちらです。
使用するGPIO番号 | 接続先 |
---|---|
D2(PA0) | LED1 |
D7(PA1) | LED2 |
さて、いつも使うデジタルピンですが、
となりのカッコ書きで表示しているものがありますね?
こちらは何かというと、実はAVRでピンの指定をするときに必要な番号なんです。
たとえばD2ピンだったら、
PA0ピンがAVR上でのピンの番号ですから、
portAの0番ピンという意味になります。
いつものとおり2,7番ピンをとソースコードに書いても何も起きないので注意です。
まずは普通にdigitalWriteしてみる。
まずは一般的なArduinoの出力をHIGH/LOWにするやり方からおさらいしましょう。
Arduinoの端子のHIGH/LOWは、digitalWriteを使用します。
具体的にはこんな感じですね。
void setup()
{
pinMode(2,OUTPUT);
pinMode(7,OUTPUT);
}
void loop()
{
digitalWrite(2,HIGH);
digitalWrite(7,HIGH);
delay(1000);
digitalWrite(2,LOW);
digitalWrite(7,LOW);
delay(1000);
}
2番pinがPA0、7番pinがPA1でしたね。
今回は一般的なArduinoのコマンドを使用するのでデジタルピンの番号を使用します。
setup関数内で、pinModeで出力モードにして、
loop関数内でHIGHやLOWにしています。
もちろん普通にやると複数のpinですから2行に分かれるわけです。
見た目では同時に光っているように見えるんですよね。
実際にずれているかどうかはオシロスコープを使わないと肉眼では厳しいです。
ショート動画を作成したので参考にしてみてください。
DIRのレジスタとOUTのレジスタを使用。
さてそれではソースコードを書いていきましょう。
どんなコードを記述すればGPIOピンを複数同時にHIGHにできるかご紹介します。
きになると思いますので、早速ソースコードをお見せします。
void setup(){
PORTA.DIR |= 0x03; // 0b00000011と同義。PA0とPA1をout出力に指定。
}
void loop(){
PORTA.OUT |= 0x03; // 0b00000011と同義。portAの0番、1番ピンをHIGHにする。
delay(1000);
PORTA.OUT &= ~0x03; // 0b00000000と同義。portAの全ピンをLOWにする。
delay(1000);
}
こんな感じです。
流れとして、DIRで出力なのか入力なのかを定義して、
実際にOUTでHIGHにしたりLOWにしたりしています。
一行で0番ピンも1番ピンも指定しているので、
同時にLEDが光るという仕組みです。
初見ではなかなか頭に入ってこないので、もう少し詳しく解説していきます。
DIRのレジスタ書き換え作業
DIRとは、arduinoの標準ライブラリでいうところの、
pinModeです。
毎回setup関数の中でpinModeが出力なのか、入力なのか指定していましたよね?
それがDIRを使うと同じポートであれば1行で記述可能です。
今回の例で行くと、
PORTA.DIR |= 0x03; // 0b00000011と同義。PA0とPA1をout出力に指定。
これは、pin0とpin1をout出力にしているので、
1bit目と2bit目を1にしています。ビットを立てるというやつです。
もちろん、PA3なんかも出力に設定する場合は、
0b00001011となり、0x0Bとすれば大丈夫です。
OUTのレジスタ書き換え作業
次にOUTです。
こちらは、digitalWriteに相当するものです。
digitalWriteは、一つのGPIOピンを指定してON/OFFしていましたが、
このOUTは、同じポートであれば1行でつまり同時にON/OFFが可能です。
DIRと同じく、該当するピンのビットを立ててあげればHIGHになります。
反対にビットを立ち下げる(0にする)ことで、出力を切ってLOWにできます。
実際に同時にHIGHになっているかオシロスコープで確認。
さて、この方法と先ほど紹介したdigitalWrite2行で書く場合、
それぞれの信号をオシロスコープで見てみましょう。
digitalWriteを2行続けて書いた場合の信号
早速オシロスコープの結果ですが、
1マス2μsなので、
1回目のdigitalWriteから3μs程度遅れてから
2行目のdigitalWriteが反応していることがわかりますね。
3μsのずれなので人間の目ではまあわからないですよね…
※3μs=0.000003秒
AVRのレジスタ操作で1行で書いた場合の信号
それではAVRのレジスタをいじって、1行で記述した場合の
オシロスコープの結果をご覧ください。
ピッタリ一致していますね。
つまり同時に複数のpinの出力がHIGHになっていると言っていいわけですね。
今回のまとめ
今回は、Arduino nano everyを使用して、
複数pinを同時にHIGI/LOWにする方法をご紹介しました。
digitalWrite2行でそのまま記述したとしても3μsのずれ量ですから、
普通の人は気にならないと思いますが、
タイミングがシビアな制御をする場合はちょっとのずれが致命傷になりかねないです。
ということなので、同時という難しい課題については、
レジスタを直接いじることによって実現可能だよ。
という紹介でした。
コメント