PIC18F14K50 7SEG 5桁 2色LEDモジュール KD26L-64を制御

icon 項目のみ表示/展開表示の切り替え

概要

監視機器用の5桁の2色7SEG LEDモジュール KD26L-6が大量に手に入ったので、手始めにPICで制御してみた。
KD26L-6はクロックとデータとラッチとGND及び赤又は緑の電源及びドライバの電源の7本のケーブルで接続する。
使用されているドライバはTOSHIBA 62705Cであり桁ごとに1個ずつ使用しており5個がカスケード接続されている。
LEDはNARG105である。赤と緑の2色表示可能なアノードコモンの7SEG LEDである。
表示データはPICのMSSPモジュールを使用する。ラッチ及び7SEG LEDのアノードはIOポートで制御する。
本プログラムでは以下の表示を繰り返します。
50から0まで100ms置きにダウンカウントする。1秒毎に赤LEDと緑LEDが入れ替わる。
0000を赤LEDで100ms置きに点滅10回、緑LEDで100ms置きに点滅10回、赤と緑を5msに交互点灯させ橙色として100ms置きに点滅10回する。
電話番号0123-45-6789を300ms置きに左スクロールこれを赤、緑、赤
16進数Fから0までのダウンカウント左スクロールその際、赤と緑を交互に表示。 ブラウザで拡大表示、又は回路図をクリックすると大きな回路図が表示されます。
1.svg

KD26L-6

ブラウザで拡大表示、又は回路図をクリックすると大きな回路図が表示されます。
2.svg

TOSHIBA 62705C

8ビットの電流値を外付け抵抗(REXT)1本で可変可能な定電流回路と、8ビットシフトレジスタ、ラッチ等で構成された定電流LEDドライバです。
KD26L-6での1セグメントあたりの電流は以下の通りです。
IOUT=/frac{1.26}{REXT}%20/times%2014.9=/frac{1.26}{860}%20/times%2014.9=21.8mA
1桁あたりドットを含めると8セグメントであり5桁なので合計40セグメントあります。
全セグメントを点灯させると
21.8mA%20/times%2040=872mA
電流を消費します。
CLOCK端子の立ち上がりエッジでシフトレジスタがシフトされます。この時SERIAL-IN(SDATA)端子のデータが取り込まれます。
LATCH端子がLレベルの時データーをホールドします。
各桁がカスケード接続されています。
3.svg
上位桁のデーターから1桁1byteのシリアルデータを全桁送信し最後にLATCH端子を一度HiにしてLowに戻すとデータが表示されます。
本回路ではSPIを利用してデータを送信します。SPIは1byteの上位ビットから送信されます。ちなみにRS232Cでは下位ビットから送信されます。
シフトレジスターの仕組みを応用すると左スクロールの場合は、1byteの新データを送信してLATCHを操作すれば簡単に実現できます。

STANLEY NARG105

1桁分の7 SEG LEDです。赤と緑それぞれアノードコモンの端子があります。
赤と緑を同時に点灯されると橙色の表示が可能です。
外形は22.8×33.0(mm)で、文字は1インチの大きさです。
アノードコモンでスタティック駆動なので全セグメントを点灯させると前項の通り872mAを駆動する必要があります。
この電流で飽和電圧が低いトランジスタ又はMOS-FETを選定する必要があります。
手持ちの中からPNP型のダーリントントランジスタである2SB1226を選択しました。コレクタの飽和電圧は0.8V程です。
放熱板無しでコレクタ損失が2Wです。全セグメント点灯時は
0.8%20/times%200.872=0.6976W
許容周囲温度は
150-/frac{150-25}{2}%20/times%200.6976=106
となります。

プログラムの説明

メインルーチン

IOポート及びMSSPの初期化を行います。
RC3 LATCH
RC7 CLOCK(MSSP)
RB7 SDATA(MSSP)
RC2 Red
RC2 Green
10進数の表示はサブルーチンword2seg7ledで設定します。
電話番号scroll表示はサブルーチンtel_dispで設定します。
16進数1桁のスクロール表示はhex_scroll_dispで設定します。

word2seg7led

変数ARGH:ARGLで示される2byteの符号なし整数をゼロパディングしてLEDに表示します。
サブルーチンword2degで2byteの符号なし整数を10進数とみなし1byteに1桁ずつの数値にメモリの下位から整数の上位桁を格納します。
サブルーチンget7seg_bitで各桁の10進データを7segデータに変換しサブルーチンspi2rwでSPIで送信し、 5桁分送信した後にサブルーチンseg7led_latchでラッチしLEDに表示させます。

word2deg

符号なし整数を10進数とみなし1byteに1桁ずつ格納します。
10で割り算をし余りをメモリの上位バイトから順番に格納します。
割り算はサブルーチンdiv16_8で行います。

get7seg_bit

WREGの16進数の値によりテーブルhex2seg7tbl を参照して1桁分のセグメント点灯データを取得します。
1桁分のセグメントデータのフォーマットは以下の通りです。
なお、点灯するセグメントは0、消灯するセグメントは1となります。
7seg.svg
ビット 7 6 5 4 3 2 1 0
セグメント a b c d e f g DOT

ソースファイル

以下のファイルで構成されている

ソースファイルのダウンロード 7seg5.zip

; 5桁7セグメントモジュール KD26L-6 表示テスト Version 1.00
; File:        7seg5.asm
; Target:      PIC18F14K50 12MHz
; アセンブラ:   Microchip MPASM(v5.51)
; 書き込み:     PICKit 3
; リリース:     2017/08/30
;
; SPIによる制御 7WH14FU->62705C ->NARG105
;
; Pin接続  
;       RC0:IO --> RED LED(J1-0) Hi:点灯,Low:消灯
;       RC1:IO --> Red 7Seg LED Power Enable(予約)
;       RC2:IO --> Green 7Seg LED Power Enable(予約)
;       RC3:IO --> LATCH(J1-3) -->黒 コネクタ1
;       RB6:MSSP ~SCK (J2-2) -->赤 コネクタ3
;       RC7:MSSP ~SDO (J1-7) -->白 コネクタ2
; SPI Timing Chart
;            LSB  MSB
;       SDO   ---<======>----<======>---
;       SCK   ~~~~~~~|___|~~~~~~~~|___|~
;
;            10000の位                                   1の位
; SDO   D0 D1 D2 D3 D4 D5 D6 D7  ----------- D0 D1 D2 D3 D4 D5 D6 D7
; LATCH ______________________________________________________________|~~|_

        #INCLUDE <p18f14k50.inc>

        ; 水晶発振(12MHz) クロック分周無 PLL無効
        ; ウォッチドッグタイマ無効 低電圧プログラム書き込みモード無効
        CONFIG FOSC = HS,CPUDIV = NOCLKDIV,PLLEN=OFF,WDTEN=OFF,LVP=OFF

;   7seg LED LATCH
LED_LATCH_BIT   EQU     3
LED_LATCH_ADS   EQU     PORTC
;   7seg LED 電源制御
LED_ADS EQU PORTC
LED_RED_ENABLE_BIT      EQU 1
LED_GREEN_ENABLE_BIT    EQU 2
;   赤LED
LED_RED_ADS EQU PORTC
LED_RED_BIT EQU 0
        
STACK_MAX   EQU d'8'    ;  スタックサイズ
COUNT_INIT  EQU d'50'   ;  カウントダウン初期値

        ; プログラムメモリのアドレスadsをTBLPTRレジスタに設定
LDTBLPTR MACRO   ads
        movlw   UPPER ads
        movwf   TBLPTRU
        movlw   HIGH ads
        movwf   TBLPTRH
        movlw   LOW ads
        movwf   TBLPTRL
        ENDM    
        
        UDATA_ACS   ; アクセスバンク
count16     RES 2      ; 表示値
wait_count  RES 3
count8      RES 1
tel_disp_v  RES 1
ARGL        RES 1
ARGH        RES 1

DIV_B       RES 1 ; 除算の除数を指定
DIV_AL      RES 1
DIV_AH      RES 1
DIV_MODL    RES 1
DIV_MODH    RES 1

buf         RES     6 ; バッファ

bank2       IDATA   060h   ;    バンク0のアクセスバンク外に割り当て
stack1      RES     STACK_MAX ; スタックエリア
        CODE
        ORG             0
        goto    start    ;   リセット時

start
        lfsr    2,stack1+(STACK_MAX-1)  ;   スタックの設定
;   IO設定
        clrf    PORTB
        movlw   b'10111111' ; RB6をデジタルIO
        movwf   ANSELH
        movlw   b'10111111' ; RB6をデジタル出力
        movwf   TRISB
        
        movlw   b'00000110'
        movwf   PORTC
        movlw   b'00001000' ; RC7,RC3,RC2,RC1,RC0をデジタルIO
        movwf   ANSEL
        movlw   b'01110000' ; RC7,RC3,RC2,RC1,RC0をデジタルIO
        movwf   TRISC
        bcf     LED_RED_ADS,LED_RED_BIT 

;   MSSPモジュール設定 CKP=1 CKE=1
        movlw   b'00110010'     ;   FOSC/64=187.5kHz CKP=1 Hi :SCKアイドル
        movwf   SSPCON1
        movlw   b'11000000'     ;   SCK立ち下がりでデーター更新 CKE=1
        movwf   SSPSTAT 

        bcf     LED_LATCH_ADS,LED_LATCH_BIT
        bsf     LED_ADS,LED_GREEN_ENABLE_BIT
;   カウントダウン表示 赤 緑
main_loop1      
        movlw   LOW COUNT_INIT
        movwf   count16
        movlw   HIGH COUNT_INIT
        movwf   count16+1
loop2
        movff   count16,ARGL
        movff   count16+1,ARGH

        call    word2seg7led

        call    wait100ms

        btfsc   buf+3,1
        bra     green_on
red_on
        bcf     LED_ADS,LED_RED_ENABLE_BIT
        bsf     LED_ADS,LED_GREEN_ENABLE_BIT
        bra     end_led
green_on
        bsf     LED_ADS,LED_RED_ENABLE_BIT
        bcf     LED_ADS,LED_GREEN_ENABLE_BIT
end_led
        decf    count16
        clrf    WREG
        subwfb  count16+1,f
        bnc     time_over
        bra     loop2
;   フラッシュ表示 赤、緑、橙
time_over
        movlw   d'10'
        movwf   count16
        bsf     LED_ADS,LED_GREEN_ENABLE_BIT
        bcf     LED_ADS,LED_RED_ENABLE_BIT
flush1_loop     
        call    wait100ms
        call    wait100ms
        btg     LED_ADS,LED_RED_ENABLE_BIT
        decfsz  count16
        goto    flush1_loop

        movlw   d'10'
        movwf   count16
        bcf     LED_ADS,LED_GREEN_ENABLE_BIT
        bsf     LED_ADS,LED_RED_ENABLE_BIT
flush2_loop     
        call    wait100ms
        call    wait100ms
        btg     LED_ADS,LED_GREEN_ENABLE_BIT
        decfsz  count16
        goto    flush2_loop

        movlw   d'10'
        movwf   count16+1
flush4_loop
        movlw   d'20'
        movwf   count16
flush3_loop     
        bcf     LED_ADS,LED_GREEN_ENABLE_BIT
        bsf     LED_ADS,LED_RED_ENABLE_BIT
        call    wait5ms
        btg     LED_ADS,LED_GREEN_ENABLE_BIT
        btg     LED_ADS,LED_RED_ENABLE_BIT
        call    wait5ms
        decfsz  count16
        goto    flush3_loop
        bsf     LED_ADS,LED_RED_ENABLE_BIT
        bsf     LED_ADS,LED_GREEN_ENABLE_BIT
        call    wait100ms
        call    wait100ms
        decfsz  count16+1
        goto    flush4_loop
;   電話番号scroll表示
tel_start       
        movlw   d'3'
        movwf   count16
        bcf     LED_ADS,LED_GREEN_ENABLE_BIT
        bsf     LED_ADS,LED_RED_ENABLE_BIT
tel_loop
        btg     LED_ADS,LED_RED_ENABLE_BIT
        btg     LED_ADS,LED_GREEN_ENABLE_BIT
        call    tel_disp
        decfsz  count16
        goto    tel_loop
;   16進数カウントダウンスクロール
        bcf     LED_ADS,LED_GREEN_ENABLE_BIT
        bsf     LED_ADS,LED_RED_ENABLE_BIT
        movlw   d'1'
        movwf   count16+1
hex_loop
        call    hex_scroll_disp
        decfsz  count16+1
        bra     hex_loop        
        goto   main_loop1

;   7Seg LED表示データをラッチするサブルーチン
seg7led_latch
        bcf     LED_LATCH_ADS,LED_LATCH_BIT
        nop     ; 666ns wait
        nop
        bsf     LED_LATCH_ADS,LED_LATCH_BIT
        return

; 16進数1桁分の表示パターンを作成するサブルーチン
; 引数 WREG 戻り値 WREG スタック1byte使用
get7seg_bit
        movwf   POSTDEC2
        LDTBLPTR hex2seg7tbl
        movf    PREINC2,w
        addwf   TBLPTRL
        clrf    WREG
        addwfc  TBLPTRH
        addwfc  TBLPTRU
        tblrd  *+
        movff   TABLAT,WREG
        return
        
hex2seg7tbl ;16進数下位1桁を7Seg点灯パターンに変換するテーブル
            ; 76543210     76543210
            ; abcdefg.     abcdefg.      Offset       各セグメント(Low:点灯,Hi:消灯)
        DB  b'00000011', b'10011111'    ; 0,1         a        D0:dot
        DB  b'00100101', b'00001101'    ; 2,3       -----      D1:g
        DB  b'10011001', b'01001001'    ; 4,5    f /    / b    D2:f
        DB  b'01000001', b'00011111'    ; 6,7     --g--        D3:e
        DB  b'00000001', b'00001001'    ; 8,9  e /    / c      D4:d
        DB  b'11000101', b'11000001'    ; a,b   -----  ○dot   D5:c
        DB  b'01100011', b'10000101'    ; c,d      d           D6:b
        DB  b'01100001', b'01110001'    ; E,F                  D7:a

;   SPI入出力サブルーチン
spi2rw
        movwf   SSPBUF
        btfss   SSPSTAT,BF
        goto    $-2
        movf    SSPBUF,w
        return   

;   電話番号scroll表示サブルーチン
tel_disp
;   全セグメント消灯
        setf    WREG
        call    spi2rw
        setf    WREG
        call    spi2rw
        setf    WREG
        call    spi2rw
        setf    WREG
        call    spi2rw
        setf    WREG
        call    spi2rw
        call    seg7led_latch
        LDTBLPTR tel_tbl
tel_disp_loop_start
        TBLRD*+
        movf    TABLAT,w
        bz      tel_disp_loop_end
        sublw   '-'
        bz      tel_disp_h
        movf    TABLAT,w    ;   数値表示
        movwf   tel_disp_v
        movf    TBLPTRU,w   ;   TBLPRTをスタックへプッシュ
        movwf   POSTDEC2
        movf    TBLPTRH,w
        movwf   POSTDEC2
        movf    TBLPTRL,w
        movwf   POSTDEC2        
        movf    tel_disp_v,w
        addlw   0d0h
        call    get7seg_bit
        movwf   tel_disp_v
        movf    PREINC2,w   ;   スタックからポップしてTBLPTRを復帰
        movwf   TBLPTRL
        movf    PREINC2,w
        movwf   TBLPTRH
        movf    PREINC2,w
        movwf   TBLPTRU
        movf    tel_disp_v,w
        bra     tel_disp_e
tel_disp_h  ;   ハイフン表示
        movlw   b'11111101'
tel_disp_e
        call    spi2rw
        call    seg7led_latch
        call    wait100ms
        call    wait100ms
        call    wait100ms
        bra     tel_disp_loop_start
tel_disp_loop_end       
        setf    WREG
        call    spi2rw
        setf    WREG
        call    spi2rw
        call    seg7led_latch
        call    wait100ms
        call    wait100ms
        call    wait100ms
        return

tel_tbl DB  "0123-45-6789",0
        
;   16進数カウントダウンスクロールするサブルーチン    
hex_scroll_disp
hex_scroll_disp_loop_a
        movlw   d'15'
        movwf   count16
hex_scroll_disp_loop_b
        movf    count16,w
        call    get7seg_bit
        bcf     WREG,0
        call    spi2rw
        call    seg7led_latch
        call    wait100ms
        call    wait100ms
        movlw   5
        movwf   count8
hex_scroll_disp_loop_c
        setf    WREG
        call    spi2rw
        call    seg7led_latch
        call    wait100ms
        call    wait100ms
        decfsz  count8
        bra     hex_scroll_disp_loop_c
        btg     LED_ADS,LED_RED_ENABLE_BIT
        btg     LED_ADS,LED_GREEN_ENABLE_BIT
        decf    count16
        bc      hex_scroll_disp_loop_b
        return

;   0.005秒待機    
wait5ms
        movlw   d'19'   ; 257μs*19=5ms
        movwf   wait_count+1
wait5ms_loop1           ; t=(12+12*count3)/12MHz 257μs
        movlw   d'0'
        movwf   wait_count+2
        nop
wait5ms_loop2
        decfsz  wait_count+2
        goto    wait5ms_loop2
        decfsz  wait_count+1
        goto    wait5ms_loop1
        return  

;   0.1秒待機      
wait100ms               ; 0.1秒Wait
        movlw   d'2'   ; 53.456ms*2=0.106912s
        movwf   wait_count
wait100ms_loop1
        movlw   d'208'  ; 257μs*208=53.456ms
        movwf   wait_count+1
wait100ms_loop2         ; t=(12+12*count3)/12MHz 257μs
        movlw   d'0'
        movwf   wait_count+2
        nop
wait100ms_loop3
        decfsz  wait_count+2
        goto    wait100ms_loop3
        decfsz  wait_count+1
        goto    wait100ms_loop2
        decfsz  wait_count
        goto    wait100ms_loop1
        return

;   2byte符号無し整数を10進数し7seg表示パターンを作成するサブルーチン
;   引数: ARGL:ARGH,変換先アドレス:FSR1 ゼロバディング
word2seg7led
        lfsr    1,buf
        call    word2deg
        lfsr    1,buf
        movf    POSTINC1,w
        call    get7seg_bit
        call    spi2rw

        movf    POSTINC1,w
        call    get7seg_bit
        call    spi2rw

        movf    POSTINC1,w
        call    get7seg_bit
        call    spi2rw

        movf    POSTINC1,w
        call    get7seg_bit
        bcf     WREG,0
        call    spi2rw

        movf    POSTINC1,w
        call    get7seg_bit
        call    spi2rw

        call    seg7led_latch
        return
        
;   2byteの符号なし整数を10進数に変換するサブルーチン(5byte) 
word2deg
        movlw  d'4'
        addwf  FSR1L
        clrf    WREG
        addwfc FSR1H

        movf   ARGL,W
        movwf  DIV_AL
        movf   ARGH,W
        movwf  DIV_AH
        movlw  d'10'
        movwf  DIV_B

        rcall  div16_8
        movf   DIV_MODL,W

        movwf   POSTDEC1
        rcall   div16_8
        movf    DIV_MODL,W

        movwf   POSTDEC1
        rcall   div16_8
        movf    DIV_MODL,W

        movwf   POSTDEC1
        rcall   div16_8
        movf    DIV_MODL,W

        movwf   POSTDEC1
        movf    DIV_AL,W

        movwf   POSTDEC1
        return  

;       除算サブルーチン  DIV_AH:DIV_AL / DIV_B  商はDIV_AH:DIV_AL   余りはDIV_MODL:DIV_MODLに返される
;       FSR2で示されるスタックを1byte使用
div16_8      ;   16bit/8bit=16bit
        clrf    DIV_MODL
        clrf    DIV_MODH
        movlw   d'16'
div16_8_loop
        movwf   POSTDEC2
        bcf     STATUS,C
        rlcf    DIV_AL
        rlcf    DIV_AH
        rlcf    DIV_MODL
        rlcf    DIV_MODH

        movf    DIV_B,W
        subwf   DIV_MODL
        btfsc    STATUS,C
        decf     DIV_MODH
        bnc     div16_8_non_sub
        bsf     DIV_AL,0
        bra     div16_8_shift
div16_8_non_sub
        movf    DIV_B,W
        addwf   DIV_MODL
                btfsc    STATUS,C
        incf    DIV_MODH
div16_8_shift
        movf     PREINC2,W
        decfsz  WREG
        bra     div16_8_loop
        return  

        END