気の向くままに辿るIT/ICT/IoT
IoT・電子工作

Arduinoで『電圧計』を作る

ホーム前へ次へ
Arduinoって?

Arduinoで『電圧計』を作る

Arduinoで『電圧計』を作る

2017/11/18

 Arduinoを使って『電圧計』を自作してみるページ。

 ここでは、最大動作電圧5V、40mA程度のArduinoボードだけで電圧を計るため、対象となる負荷は乾電池1〜3本くらいしか計測できませんが(入力電圧を分圧、逆算すれば5V以上もいけるのね...)、マルチメータがなくても、また、あったとしてもこれと比較できますし、マルチメータがなく乾電池残量チェッカーを持っているとしても数値の目盛りがないことが多いでしょうから、電圧値を確認できるのはメリットと言えるでしょう。

 と言ってもArduinoによる電圧計は定番中の定番というか、電流センサ含め、電力計を作る情報さえ既に多々あります。

 それでも敢えて記事にしようと思ったのは、少なくともそれぞれ複数ある手持ちのArduino UnoとPro Miniでは小数点第3位で切り上げたのか、微妙な測定誤差なのか、x.xxにはなるものの、精度は高く、正確なのに、なぜか、Arduino Nanoだと、ある意味正確に0.09V程(高めに)差が出たよという状況に遭遇したから。

Arduino電圧計の回路とスケッチ

 まずは、とりあえず、回路とスケッチ例を示しておきます。

void setup() {
  Serial.begin(9600);
}
 
void loop() {
  double val = analogRead(A0);
  val *= 5;
  val /= 1024;
  if(val > 0) {
  Serial.print("Voltage : ");
  Serial.print(val);
  Serial.println(" V");
  delay(1000);
  }
}

 回路は、Arduinoボードの(任意のアナログピン)A0とGNDにつないだジャンパワイヤのオスピンを、それぞれ乾電池(や電池ボックスの)+とーにつなぐだけ。

 ただ、それだけだと何もしていない(無負荷)時に値が変動するので、これを回避するためには1kΩ〜10kΩ程度の抵抗をA0とGND間に入れておきます。

 スケッチは、これだけで、アナログ値は0-1023の1024、実際の入力値にArduinoボードで最大許容動作電圧の5Vを乗じ、1024で割れば、実際の電圧値を求めることができます。

 if文は、値の出力をわずかながらでも抑制できるかな?と思って入れてあるだけ。

 これでボードやシリアルポートを指定してシリアルモニタを開き、乾電池(や相応の電池をセットした電池ボックス)のプラス、マイナスにジャンパワイヤのピンを当てればシリアルモニタ上に電圧値が表示されます。

デジタルマルチメータでのとある単3乾電池計測結果

 デジタルマルチメータで計ると1.373Vの電池は...

Arduino IDEシリアルモニタでのとある単3乾電池計測結果表示

 シリアルモニタ(Arduino Unoによる電圧計)では、1.38V...

0.91インチLCDでのとある単3乾電池計測結果表示

 出力元が同じであるため、当然ではありますが、0.91インチLCD 128x32(Arduino Unoによる電圧計)でも1.38V...

となり、正確(というか使用したデジタルマルチメータとほぼ同値、近似)。

#include <SPI.h>
#include <Wire.h>
#include <Adafruit_GFX.h>
#include <gfxfont.h>
#include <Adafruit_SSD1306.h>
 
#define OLED_RESET 4
Adafruit_SSD1306 display(OLED_RESET);
 
#define NUMFLAKES 10
#define XPOS 0
#define YPOS 1
#define DELTAY 2
 
#define LOGO16_GLCD_HEIGHT 16
#define LOGO16_GLCD_WIDTH  16
static const unsigned char PROGMEM logo16_glcd_bmp[] =
{ B00000000, B11000000,
  B00000001, B11000000,
  B00000001, B11000000,
  B00000011, B11100000,
  B11110011, B11100000,
  B11111110, B11111000,
  B01111110, B11111111,
  B00110011, B10011111,
  B00011111, B11111100,
  B00001101, B01110000,
  B00011011, B10100000,
  B00111111, B11100000,
  B00111111, B11110000,
  B01111100, B11110000,
  B01110000, B01110000,
  B00000000, B00110000 };
 
#if (SSD1306_LCDHEIGHT != 32)
#error("Height incorrect, please fix Adafruit_SSD1306.h!");
#endif
 
void setup() {
  // put your setup code here, to run once:
  Serial.begin(9600);
 
  // by default, we'll generate the high voltage from the 3.3v line internally! (neat!)
  display.begin(SSD1306_SWITCHCAPVCC, 0x3C);  // initialize with the I2C addr 0x3C (for the 128x32)
  // init done
  
  // Show image buffer on the display hardware.
  // Since the buffer is intialized with an Adafruit splashscreen
  // internally, this will display the splashscreen.
  display.display();
  delay(2000);
 
  // Clear the buffer.
  display.clearDisplay();
 
}
 
void loop() {
  // put your main code here, to run repeatedly:
 
  double val = analogRead(A0);
  val *= 5;
  val /= 1024;
//  val -= 0.09; // Nanoの誤差調整
  if(val > 0) {
    Serial.print("Voltage : ");
    Serial.print(val);
    Serial.println(" V");
 
    display.setTextSize(2);
    display.setTextColor(WHITE);
    display.setCursor(10,0);
    display.print("Voltage : ");
    display.print(val);
    display.println(" V");
    display.display();
    delay(1000);
    display.clearDisplay();
  }
}

 Adafruit_SSD1306Adafruit-GFX-Libraryを使った0.91インチLCDを含むラフスケッチがこれです。

 サンプルスケッチssd1306_128x32_i2cをザッと眺めつつ切り貼りしてみたのですが、当検証はできたものの、精査していないため余計な行も含まれると思われます。

Arduino Nanoの?互換機の?特定個体の?謎

Arduino Nano+0.91インチLCDでのとある単3乾電池計測結果表示

 さて、冒頭述べた通り、この電圧計測において、もちろん、同じ乾電池なのにNanoだけアナログ入力値*5/1024の算出値が0.09程度ズレるという現象に遭遇することになりました。

 ほかは定数なので要するにアナログ値に誤差があるということになります。

 このところ、検証には、UnoよりもNanoを使うことが増えてきていたのですが、今回も最初にNanoで試してみたところ、手持ちのデジタルマルチメータと差が出たことから、マルチメータの精度もそんなに高くないのかも?なんて思いつつ、UnoやPro Mini、他のNanoなど他のArduinoボードで試してみたところ、この誤差はNanoだけに発生することがわかりました。

 これらのArduino Nanoは、以前、Amazon/Hiletgoで買ったものでHiletgoがプライム(というかAmazon発送)対応する前でマーケットプレイス直だった当時、ピンヘッダ半田付け済みのものと未ハンダのものが(なぜか、前者の方が安価で)同店で売られており、今回検証に使った2つは、たまたま、この2種類、つまり、1つは購入後、自分ではんだ付けしたもの。

 自身の半田付けは未だ完璧ではなく、自分でも呆れるほどいつまで経っても上達しないのですが、半田付け済みのものは、ほぼ完璧に見える、共に他では不具合等出ていない、2種類共にアナログピン位置を変えて試しても同様に算出後(アナログ値x5/1024)の差分が、やはり、0.09ほどという点からも、はんだ付けに起因するものではないと思われます。

 より正確には、最初はNanoを1個試して同現象が発生したため、2個ある内、一方のUnoで試すと値は想像以上に正確、後日、未ハンダだったNano 1個とPro Mini 3個を半田付け、確認したところ、Pro Miniも正確で、Nanoだけ0.09くらい誤差が出たという次第。

 これらのことから、Nanoボードのアナログ入力回路部分に起因するのか?とも思いますが、判別できるほど熟達しておらず、ハズレの個体なのか、Hiletgoで販売のものだけなのか、(特に中華系だと仕入元が同じ可能性もあって正確に分類は難しいですが)他互換機も同じなのか、はたまたオリジナルもなのかについては手持ちもないのでわかりません。

 まぁ、少なくとも手持ちのものについては、他でアナログ値に依存するスケッチを書いた際にもこの誤差を意識しておく必要はありますが、差分がほぼ同じだからスケッチ上で0.09ほど差し引いておけば、よいという話もなくもないのですが。(と言っても上記スケッチで差し引くと、なぜか、表示上、ちょっと微妙なことになる...。)

 仮にマルチメータ持ってなくてArduinoボードもこのNanoしかなくて、この回路組んで電圧測ってたら気づかないところだった...比較検証って重要だなと改めて思いました。

 あ、他にも半田付け済みのNanoが2個あり、Arduino ISPとKyutech Arduino Scopeのケーシングもした試作機で使っていますが、オシロはアナログ入力を使ってるから、手持ちのNano互換機共通の現象だとしたら、この誤差の影響を受けるってことか...。

 尤もDMMやUNO、Pro Miniの結果が正しいとも限らず、Nanoのみ正確という可能性もなくもありませんが、ここは多数決ということで...。

[2017/11/21]
Arduino回転計測器のブレッドボードを微整理

 この点は、なんとかするとしてLCDをはみ出すことなく同じブレッドボード上に載せることにし、プローブ?部だけ少し長くしつつ、他を短いジャンパワイヤに替えてブレッドボード上を少しだけ整理。

Arduino回転計測器をケースに格納

 そして100均トレカケースでケーシングしてみました。

 ブレッドボードは、裏面の両面テープの剥離紙を剥がして貼っただけ。

 USBコネクタ部の穴と外だしするジャンパワイヤ用の溝には、相変わらず横着して加工用にしてあるハンダゴテを使用。

 ちなみにUSBミニ/USB Aケーブルも100円ショップセリアで購入、Android用一口AC電源接続USB充電器もダイソーの200円商品、左端にある方眼シート、中央の回転台(ターンテーブル?)、黄緑の鍋敷きシリコンシート、滑り止めマット、先の30W加工用ハンダゴテも...。

ホーム前へ次へ