フォト
2017年3月
      1 2 3 4
5 6 7 8 9 10 11
12 13 14 15 16 17 18
19 20 21 22 23 24 25
26 27 28 29 30 31  
無料ブログはココログ

« Arduinoで16x16 LEDドットマトリックスを利用する(5) | トップページ | OCN モバイル ONEが通信容量増量 »

2014年10月 2日 (木)

Arduinoで16x16 LEDドットマトリックスを利用する(6)

Dscn3081

前回の続きです。

スクロール表示の動作検証および、日本語フォントROM GT20L16J1Yを使ってみました。
割り込み処理とSPI通信の併用を心配していましたが、まったく問題なしでした。

動画の"こんにちは埼玉県"は、arduinoのSRAMにあるフォントデータを利用しています。
"色は..."のいろは歌はSPI接続のフォントROM  GT20L16J1Yを参照して文字を
表示しています。

スクロールをちょと速めにしてもちゃんと表示出来ています。
GT20L16J1Yは3.3V駆動なので、CD4050を使って5V -> 3.3Vのレベル調整をしました。

Photo_2

LED表示部は前回と変わらずですが、清書しました。
清書してD9接続の74HC595とTB62706のLATCHのタイミングが違うことに初めて気づきました。
まあ、動作しているのでOKということで..(タイミング的にも大丈夫なはず)。

Photo_3

プロフラムソースはこんな感じです。

//
// TB62706を使ったLEDの点灯サンプル
//

#include <arduino.h> #include <MsTimer2.h> #include <string.h> #include <SPI.h> /// #define ASC8x16S 255968  // 8x16 ASCII 粗体字符(半角) #define ASC8x16N 257504  // 8x16 ASCII 日文假名(半角) #define DATAPIN (7) // TB62706のSERIAL-INへ #define LATCHPIN (9) // TB62706のLATCHへ #define CLOCKPIN (8) // TB62706のCLOCKへ #define ENABLEPIN       (6)     // TB62706のENABLEへ uint16_t fbuf[16];    // 表示パターンバッファデータ byte rowdata[32];     // 漢字ROM読み取り用バッファ // 文字データ "こんにちは埼玉県" uint16_t fnt[11][16]= { {// ""   0xffff,0xffff,0xffff,0xffff,0xffff,0xffff,0xffff,0xffff,   0xffff,0xffff,0xffff,0xffff,0xffff,0xffff,0xffff,0xffff },   {// こ   0x0000,0x0000,0x1ff8,0x0000,0x0000,0x0000,0x0000,0x0000,   0x0000,0x0000,0x2000,0x3000,0x1c00,0x07fc,0x0000,0x0000 }, {// ん   0x0200,0x0200,0x0600,0x0400,0x0c00,0x0800,0x0800,0x1b80,   0x1440,0x1840,0x3040,0x2042,0x2046,0x604c,0x4038,0x0000 }, {// に   0x0000,0x1000,0x1000,0x31fc,0x2000,0x2000,0x2000,0x2000,   0x2000,0x2000,0x2200,0x2200,0x2b00,0x31fe,0x1000,0x0000 }, {// ち   0x0100,0x0100,0x0100,0x7ffc,0x0200,0x0600,0x0400,0x0ff0,   0x1808,0x3004,0x0004,0x0004,0x000c,0x0038,0x07e0,0x0000 }, {// は   0x0000,0x2020,0x2020,0x6020,0x47fe,0x4020,0x4020,0x4020,   0x4020,0x4020,0x43e0,0x4438,0x542c,0x6466,0x23c0,0x0000 }, {// 埼   0x2020,0x2020,0x23fe,0x2050,0xf8d8,0x218c,0x2000,0x27ff,   0x2004,0x21e4,0x3924,0x6124,0xc124,0x01e4,0x0004,0x001c}, {// 玉   0x0000,0x7ffe,0x0100,0x0100,0x0100,0x0100,0x0100,0x3ffc,   0x0100,0x0100,0x0118,0x010c,0x0104,0x0100,0xffff,0x0000 }, {// 県   0x07f8,0x2408,0x2408,0x27f8,0x2408,0x2408,0x27f8,0x2408,   0x2408,0x27f8,0x2000,0x3fff,0x0888,0x188c,0x7087,0x0080 }, {// ""   0x0000,0x0000,0x0000,0x0000,0x0000,0x0000,0x0000,0x0000,   0x0000,0x0000,0x0000,0x0000,0x0000,0x0000,0x0000,0x0000 }, {// ""   0xAAAA,0x5555,0xAAAA,0x5555,0xAAAA,0x5555,0xAAAA,0x5555,   0xAAAA,0x5555,0xAAAA,0x5555,0xAAAA,0x5555,0xAAAA,0x5555 } }; //いろは歌(JISコード文字列) uint16_t iroha[] = {   0x3f27,0x244f,0x244b,0x245b,0x2458,0x2449,0x3b36,0x246a,//1   0x244c,0x246b,0x2472,0x3266,0x242c,0x4024,0x243f,0x246c,//2   0x243e,0x3e6f,0x244a,0x2469,0x2460,0x4d2d,0x3059,0x244e,//3   0x317c,0x3b33,0x3a23,0x467c,0x315b,0x2428,0x2446,0x4075,//4   0x242d,0x4c34,0x382b,0x2438,0x3f6c,0x2452,0x2462,0x243b,//5   0x243a }; // 漢字ROM  GT20L16J1Y用 // 全角JISコードからフォント格納先頭アドレスを求める //   GT20L16J1Y データシート VER 4.0 2013-3のサンプルを参照した //   (サンプルでは区点コードからの変換であることに注意) unsigned long calcAddr(unsigned short jiscode) {   unsigned long MSB;      unsigned long LSB;   unsigned long Address;   char buf[32];   // 上位、下位を区点コードに変換   MSB = (jiscode >> 8) - 0x20;   LSB = (jiscode & 0xff) -0x20;     // データ格納アドレスを求める   if(MSB >=1 && MSB <= 15 && LSB >=1 && LSB <= 94)     Address =( (MSB - 1) * 94 + (LSB - 01))*32;   else if(MSB >=16 && MSB <= 47 && LSB >=1 && LSB <= 94)     Address =( (MSB - 16) * 94 + (LSB - 1))*32+43584;   else if(MSB >=48 && MSB <=84 && LSB >=1 && LSB <= 94)     Address = ((MSB - 48) * 94 + (LSB - 1))*32+ 138464;   else if(MSB ==85 && LSB >=0x01 && LSB <= 94)     Address = ((MSB - 85) * 94 + (LSB - 1))*32+ 246944;   else if(MSB >=88 && MSB <=89 && LSB >=1 && LSB <= 94)     Address = ((MSB - 88) * 94 + (LSB - 1))*32+ 249952;     return Address; } // 漢字ROM  GT20L16J1Y用 // JISコードからキャラクタデータを得る void getCharData(unsigned short code) {     byte data;     unsigned long addr=0;     byte n;     if (code > 0xFF) {       // 全角       addr =calcAddr(code);       n = 32;     } else {       // 半角       addr = ASC8x16N + (code<<4);       n = 16;     }         digitalWrite(10, HIGH);     //delayMicroseconds(10);        digitalWrite(10, LOW);     SPI.transfer(0x03);     SPI.transfer((addr>>16) & 0xff);     SPI.transfer((addr>>8) & 0xff);     SPI.transfer(addr & 0xff);     SPI.setBitOrder(LSBFIRST);         for(byte i = 0;i< n; i++)       rowdata[i] = SPI.transfer(0x00);         SPI.setBitOrder(MSBFIRST);     digitalWrite(10, HIGH); } // 漢字ROM  GT20L16J1Y用 // 漢字ROMフォントを表示用形式に変換する void rowtofont(uint16_t* fnt) {   for (byte i=0; i <16; i++)     fnt[i]=0;     for (byte i=0;i<8;i++)     for (byte j=0; j<16; j++) {         fnt[7-i] |= (rowdata[j] & 0x1<<i ? 0x8000: 0) >>j;         fnt[15-i] |= (rowdata[j+16] & 0x1<<i ? 0x8000: 0) >>j;     }    } // 漢字ROM  GT20L16J1Y用 // JIS漢字コートに対応するフォントデータの取得 // void loadfontdata(uint16_t *fnt, unsigned short code) {    getCharData(code);    rowtofont(fnt);       } // 漢字ROM  GT20L16J1Y用 // 漢字ROMを参照してフォントを表示する void test_iroha() {   uint16_t buf[16];   for (int i=0; i <41; i++) {     loadfontdata(buf, iroha[i]);     setfontscl(buf, 25);   } } // // 行の指定 // void selectRow(byte no) {         uint16_t val = _BV(15-no);         // ビット列データの出力 for( byte i = 0; i < 16; i++ ){ digitalWrite(DATAPIN, val & _BV(i) ? 1:0); digitalWrite(CLOCKPIN, HIGH); digitalWrite(CLOCKPIN, LOW); } } // // 行フォントパターンの送信 // void dataOut(uint16_t val ) { for( byte i = 0; i < 16; i++ ){ digitalWrite(DATAPIN, val & _BV(i) ? 1:0); digitalWrite(CLOCKPIN, HIGH); digitalWrite(CLOCKPIN, LOW); } } // // バッファ内データを表示する // void fontout() {     // 点灯LEDが移動するパターン     digitalWrite(ENABLEPIN,LOW);            // OUTを有効にする     for( byte i = 0; i < 16; i++ ) {        digitalWrite(LATCHPIN, LOW); //送信開始               selectRow(i);                    dataOut(fbuf[i]);        digitalWrite(LATCHPIN, HIGH); //送信開始             }     digitalWrite(ENABLEPIN,HIGH);            // OUTを有効にする } // // バッファにフォントパターンをセット // void setfont(uint16_t* fptr) {   memcpy(fbuf, fptr, 32);  } // // バッファ内の指定座標に点をセット // void setdot(uint8_t x, uint8_t y, byte dot) { // uint16_t v = ;   fbuf[y] = dot ? fbuf[y]| (0x8000>>x): fbuf[y] & ~(0x8000>>x); } void testdotset() {   for (byte y=0; y<16; y++) {     for (byte x=0; x<16; x++) {       setdot(x,y,1);       delay(10);     }   }   for (byte y=0; y<16; y++) {     for (byte x=0; x<16; x++) {       setdot(x,y,0);       delay(10);     }   } } // // 指定座標にフォントパターンをセット // void setfontat(uint16_t* fptr, uint8_t x, uint8_t y) {   uint16_t w;     if (x>15 || y >15)     return;       for (byte j=y,i=0; j < 16; j++,i++)     fbuf[j] = (fbuf[j]>>(16-x))<<(16-x) | fptr[i]>>x; } void test01() {   for (byte i=0; i <11; i++) {     for (byte x=15; x > 0; x--) {       setfontat(fnt[i],0,x);       delay(20);     }   } } // // ドット表示チェック(デバッグ用) // void dottest() {   for (byte y=10; y < 11;y++)     for (byte x=0;x <16;x++) {       fbuf[y]= 0x8000>>x;      delay(50);       fbuf[y]= 0;     }        } // // バッファーデータのスクロール // h_mode : 0 なし,1 左 ,2 右 // v_mode : 0 なし,1 上, 2 下       // void scroll(uint8_t h_mode, uint8_t v_mode) {   if (h_mode ==1)     for (byte i = 0; i < 16; i++)       fbuf[i] = fbuf[i]<<1;   if (h_mode ==2)     for (byte i = 0; i < 16; i++)       fbuf[i] = fbuf[i]>>1;   if (v_mode ==1) {     for (byte i = 0; i < 15; i++)      fbuf[i]= fbuf[i+1];     fbuf[15]=0;   }   if (v_mode == 2) {     for (byte i = 15; i >0; i--)      fbuf[i]= fbuf[i-1];     fbuf[0] = 0;      } } // スクロールテスト void test02() {     byte i;     setfont(fnt[6]);     for (i=0; i<16;i++) {       scroll(1,0);       delay(50);     }     delay(200);     setfont(fnt[6]);     for (i=0; i<16;i++) {       scroll(2,0);       delay(50);     }     delay(200);     setfont(fnt[6]);     for (i=0; i<16;i++) {       scroll(0,1);       delay(50);     }     delay(200);             setfont(fnt[6]);     for (i=0; i<16;i++) {       scroll(0,2);       delay(50);     }     delay(200);         setfont(fnt[6]);     for (i=0; i<16;i++) {       scroll(1,1);       delay(50);     }     delay(200);     setfont(fnt[6]);     for (i=0; i<16;i++) {       scroll(2,2);       delay(50);     }     delay(200); } // // スクロールしながらパターンを表示 // void setfontscl(uint16_t* fptr, uint16_t dly) {   for (byte i=0; i<16; i++) {     scroll(1, 0);     setfontat(fptr, 15-i, 0) ;     delay(dly);   } }  void setup() {     pinMode(10,OUTPUT);     SPI.begin();     //SPI.setClockDivider(SPI_CLOCK_DIV4);         pinMode(ENABLEPIN,OUTPUT);     pinMode(DATAPIN, OUTPUT);     pinMode(LATCHPIN, OUTPUT);     pinMode(CLOCKPIN, OUTPUT);     digitalWrite(ENABLEPIN,HIGH);     digitalWrite(CLOCKPIN, LOW);     digitalWrite(LATCHPIN, HIGH);      digitalWrite(ENABLEPIN,LOW);         // OUTを有効にする      setfont(fnt[9]); // フォントバッファに初期パターン設定           // 割り込み開始      MsTimer2::set(15, fontout); // 1/60秒程度で1文字を表示      MsTimer2::start(); } void loop(){   test_iroha();  // いろは歌表示(漢字ROM利用)   delay(1000);   test02();      // スクロールテスト   testdotset();  // ドット単位アクセス表示   // 配列格納文字パターンを順番に表示する   for (byte i =0; i < 11; i++)     setfontscl(fnt[i],40); } 

 

arduinoの文字列がUTF8を使っているのに対して、漢字フォントROMはJISコードなので、
プログラムで「はいろは歌」の文字列をJISコードにて保持して表示しています。
この点はちょっと面倒です。 この対応を模索しています。

「Arduinoで16x16 LEDドットマトリックスを利用する(7)」 に続きます。

« Arduinoで16x16 LEDドットマトリックスを利用する(5) | トップページ | OCN モバイル ONEが通信容量増量 »

arduino」カテゴリの記事

AVR」カテゴリの記事

表示器制御関連」カテゴリの記事

コメント

コメントを書く

(ウェブ上には掲載しません)

トラックバック

この記事のトラックバックURL:
http://app.cocolog-nifty.com/t/trackback/571408/60411436

この記事へのトラックバック一覧です: Arduinoで16x16 LEDドットマトリックスを利用する(6):

« Arduinoで16x16 LEDドットマトリックスを利用する(5) | トップページ | OCN モバイル ONEが通信容量増量 »