JH7UBCブログ

アマチュア無線 電子工作 家庭菜園など趣味のブログです

Arduino MAX7219使用8桁7セグメントLED表示テストその2

2022-09-10 23:19:30 | Arduino
 前の記事で、任意のdigitに数字を表示するテストをしました。
 今回は、数値を任意の位置に表示するテストをします。表示範囲に右詰めで表示します。

 Arduinoと8桁7セグメントLEDモジュールとの接続は、前の記事と同じです。
 下の図のように、digit xから幅nl桁に数値を表示します。



 スケッチです。
  例として、digit5から4桁で0.5secごとにカウントアップする数値を右詰めで表示してみます。
 数値を一旦文字列に変換し、Stringクラスで処理を行います。lnは実際の文字列の長さです。文字列から1文字ずつsubstring()でとりだします。取り出した文字は、数値に変換してLED表示します。ゼロ消しは、プログラムで行っています。(2022.09.13 スケッチの一部を修正しました。)
-------------------------------------------------------------------
/*
 * Arduino MAX7219 7seg LED test
 * 2022.09.13
 * JH7UBC Keiji Hata
 */

#include <SPI.h>
#define CS_PIN 10
//CLK PIN13
//DIN PIN11

// MAX7219 Register Address
#define MAX7219_DECODE_MODE 0x09
#define MAX7219_INTENSITY 0x0a
#define MAX7219_SCAN_LIMIT 0x0b
#define MAX7219_SHUTDOWN 0x0C
#define MAX7219_DISPLAY_TEST 0x0f

void maxTransfer(uint8_t address, uint8_t value) {
  digitalWrite(CS_PIN, LOW);  // Start transfer.
  SPI.transfer(address);      // Send address.
  SPI.transfer(value);        // Send the value.
  digitalWrite(CS_PIN, HIGH); // Finish transfer.
}

void MAX7219_INI(){
  maxTransfer(MAX7219_DECODE_MODE, 0xff);// Code B decode for digits 7–0
  maxTransfer(MAX7219_INTENSITY, 0x03); // Intensity
  maxTransfer(MAX7219_SCAN_LIMIT, 0x07);// Display digits 01234567
  maxTransfer(MAX7219_SHUTDOWN, 0x01);// Normal Operation
  maxTransfer(MAX7219_DISPLAY_TEST, 0x00);// Normal Operation
}

void Clear_Display(){
  for(uint8_t i=1;i<=8;i++){
    maxTransfer(i,0x0f);
  }
}
void setup() {
  pinMode(CS_PIN, OUTPUT);     // CS_Pin is OUTPUT Mode
  digitalWrite(CS_PIN, HIGH);  // CS=HIGH
  SPI.setBitOrder(MSBFIRST);   // Reverse the SPI Data o/p.
  SPI.begin();                 // Start SPI
  MAX7219_INI();
  Clear_Display();
}

//x=表示開始digit(digit7-0)、nl=数値の最大長、num=表示する数値
//数値は右詰めで表示する
void printnum(uint8_t x,uint8_t nl,uint16_t num){
  String s=String(num); //数値を文字列に変換
  uint8_t ln=s.length();//文字列の長さ
  int ix=ln-nl;     //index初期値
  uint8_t sx=x+1;       //表示開始アドレス

  for(uint8_t i=0;i<nl;i++){
    int index=ix+i;
    if(index<0){
      maxTransfer(sx-i,0x0f);
    }else{
      String c=s.substring(index,index+1);//indexの文字を1個取り出す
      uint8_t m = c.toInt();//文字列を数値に変換
      maxTransfer(sx-i,m);
    }
  }
}

void loop() {
  for(uint16_t i=0;i<10000;i++){
    printnum(5,4,i);
    delay(500);
  }
}
-------------------------------------------------------------------
 表示している様子です。


Arduino MAX7219使用8桁7セグメントLED表示テストその1

2022-09-09 19:36:24 | Arduino
 ArduinoでMAX7219を使った8桁7セグメントLEDの表示テストをしました。
 このLEDは、Amazonから購入しましたが、中国からの発送なので、到着まで約3週間かかりました。こちらの商品で、2個で499円でした。


 表面です。8桁で約7cmの幅です。使いやすい大きさですね。
 LEDは、右からDigit0,1,2,3...7です。


裏面です。MAX7219コントローラが搭載されています。

 このモジュールとの通信は、SPI通信で、DIN,CS,CLKの3つの信号で、コマンドとデータを送ります。Arduinoとの接続回路図です。
Arduino   8X7seg_LED
5V      VCC
GND     GND
D11(MOSI)  DIN
D10(CS)   CS
D13(SCK)   CLK



 このモジュールを使うためのライブラリは、Arduinoでは、ライブラリマネージャーに「MAX7219」と入力して検索すれば簡単に見つけることができますし、Web上でも紹介されています。私もこのライブラリのサンプルプログラムで、表示を確認しました。

 今回は、あえてライブラリを使わないで表示テストをします。というのは、MAX7219の動作については、このブログの「Arduino 8X8LED MAX7219テスト その1」という記事で勉強しましたので、比較的簡単に動作させることができると考えたことと、ライブラリを使わないプログラムであれば、他のマイコン(PICやRaspberry Pi Picoなど)への移植もできると考えたからです。

 例として、digit3に5を表示してみましょう。
 MAX7219に送るデータは16ビットで、下の表1ようなフォーマットになっています。送信する順序は、D15,D14,.......D1,D0と最上位ビットから送信します。従って、上位8ビット(SDDRESS)、下位8ビット(DATA)の順にMSBFIRSTで送信します。


 D8-D11は、レジスタのアドレスで、表2のように割り当てられています。
 Digit3のアドレスは、0x04です。
 次に「5」を表示するには、DATAに0101=5を送ります。

 スケッチです。
 0.5secごとに、Digit3に「5」を表示し、次にdotを付け加え、次に空白(blank)を表示(数字を消す)させています。
 dot(デシマルポイント)を表示させるには、D7=1とすればよく、表示データに0x80を加えます。また、blankは、0x0fをデータとして送ります。
--------------------------------------------------------------------------------------------
/*
 * Arduino MAX7219 7seg LED test
 * 1桁表示テスト
 * 2022.09.08
 * JH7UBC Keiji Hata
 */

#include <SPI.h>
#define CS_PIN 10
//CLK PIN13
//DIN PIN11

// MAX7219 Register Address
#define MAX7219_DECODE_MODE 0x09
#define MAX7219_INTENSITY 0x0a
#define MAX7219_SCAN_LIMIT 0x0b
#define MAX7219_SHUTDOWN 0x0C
#define MAX7219_DISPLAY_TEST 0x0f

void maxTransfer(uint8_t address, uint8_t value) {
  digitalWrite(CS_PIN, LOW);  // Start transfer.
  SPI.transfer(address);      // Send address.
  SPI.transfer(value);        // Send the value.
  digitalWrite(CS_PIN, HIGH); // Finish transfer.
}

void MAX7219_INI(){
  maxTransfer(MAX7219_DECODE_MODE, 0xff);// Code B decode for digits 7–0
  maxTransfer(MAX7219_INTENSITY, 0x03); // Use lowest intensity.
  maxTransfer(MAX7219_SCAN_LIMIT, 0x07);// Display digits 01234567
  maxTransfer(MAX7219_SHUTDOWN, 0x01);// Normal Operation
  maxTransfer(MAX7219_DISPLAY_TEST, 0x00);// Normal Operation
}

void Clear_Display(){
  for(uint8_t i=1;i<=8;i++){
    maxTransfer(i,0x0f);
  }
}
void setup() {
  pinMode(CS_PIN, OUTPUT);     // CS_Pin is OUTPUT Mode
  digitalWrite(CS_PIN, HIGH);  // CS=HIGH
  SPI.setBitOrder(MSBFIRST);   // Reverse the SPI Data o/p.
  SPI.begin();                 // Start SPI
  MAX7219_INI();
  Clear_Display();
}

void loop() {
    maxTransfer(4,5);//digit4に5を表示
    delay(500);
    maxTransfer(4,5+0x80);//小数点を加える
    delay(500);
    maxTransfer(4,0x0f);//表示を消す(ブランク表示)
    delay(500);
}
--------------------------------------------------------------------------------------------


 表示結果です。


県北430CQ大会終了

2022-09-05 12:17:59 | アマチュア無線
 9月2日(金)18:00から4日(日)21:00まで第32回県北430CQ大会が開催されました。
 この大会は、430MHzのFMモードだけを使うユニークなコンテストです。当局は3日間、主に夜7時ころから9時ころまで参加し430MHzでの交信を楽しみました。

 ただ、2日目の夜は、こちら喜多方市は雨になりました。雨が降ると私のアンテナ(22mH 20エレスタック)は、SWRが上がり飛びが悪くなります。CQを出すも応答はなく、CQ局をコールしてもコールバックがありません。ということで、ほとんど交信することができませんでした。残念。

 3日間で35局と交信することができました。交信いただいた各局ありがとうございました。

10月26日追記
 10月20日に結果が発表されました。当局は26局中12位でした。
 詳しくは、県北430CQクラブのホームページをご覧ください。