【パターン1の処理】
パターンの処理はサブルーチンとすることにしました。これで
パターン処理を独立に考えることが出来ます。
パターン1の処理は
「キースイッチ1を押している間、8個の発光ダイオードが1個
づつ順に1秒間隔で点灯する。」というものです。
前ページで作成したフローチャートに従ってコーディングします。
つまりプログラムを書いて行きます。
まず、変数を決めます。変数として必要なのは、下記だけです。
結局最初に変数として宣言した「DATA」は使わないで出来ること
になりました。
BITC:ビット位置カウンター
まず、最初に既に8ビット目まで完了したかを確認し、完了して
いたら0ビット目に戻ってやり直します。
この処理が最初に来るのはおかしい感じがしますが、このパターン
の処理はキースイッチ1が押されている間は何回も繰り返し実行
され、その度ごとにBITCが+1だけカウントアップされるので、
まず最初に何回目かを調べる訳です。
ここで、では一番最初のBITCの値は? という問題が出てきます。
そこで必要になるのが初期化で、BITCを最初0クリアする命令を
初期化に加える必要が出てきました。
初期化部に下記を追加します。
CLRF BITC ;初期クリア
さて8回目かという判定部分を命令で書くと、下記となります。
PATAN1 ;パターン1の先頭ラベル
MOVLW 8 ;8回
SUBWF BITC,W ;BITC-8
BTFSS STATUS,C ;BITC>8 つまり8回目では無い
CLRF BITC ;0ビット目に戻す
(実はこの部分は間違っている)
次はいよいよ発光ダイオードの点灯制御です。
これにはPORT BのBITCだけ「0」にし、残りは「1」にすれば良い
のですから、一度全ビット「1」にしたあとで、BITCビット目だけ
「0」にするようにします。これを命令で書くと下記となります。
MOVLW 0FFH ;全ビット1にする
MOVWF PORTB ;PORTBに出力
BCF PORTB,BITC ;BITCビット目だけ0にする
(実はここも間違っています)
これで制御が完了しましたから、あとは、次に備えてBITCを+1
しておき、さらに1秒間の待ちを挿入します。
ここでBITCはどうなるかというと、最初は0で1ビット目の発光
ダイオードを制御したあと+1されるので「1」となっています。
また最後は8ビット目の発光ダイオードを制御したあと8となって
います。
プログラムは下記の様に書きます。つまり1秒待ちはサブルーチン
として扱います。
INCF BITC,F ;BITCの内容を+1する
CALL T1SEC ;1秒タイマー
RETURN ;終了戻り
パターン2も同じように考えて行きます。まずパターン2は下記条件
となっています。
「キースイッチ2を押している間、8個の発光ダイオードが順に
1個づつ点灯していき、全部点灯したら一旦全消灯し繰り返す。」
まず初期化のところで全消灯されている状態から始まるとします。
そして必要な変数はやはりビットカウンターである「BITC」だけ
となります。
最初の所でパターン1と同じように8回目かどうか判定し、8回目
だったら、BITCを0に戻すと同時に、全消灯する制御を行います。
これをプログラムで書くと、8回目という判定の仕方がちょっと
異なりますが、この辺りが間違いやすい所です。
つまり「より大」か「以上」かという違いです。
PATAN2
MOVLW 7 ;8回
SUBWF BITC,W ;BITC-7
BTFSC STATUS,C ;BITC<7 つまり8回目でスキップ
GOTO PTN2LP ;そのまま制御へジャンプする
CLRF BITC ;0ビット目に戻す
MOVLW 0FFH ;全ビット1
MOVWF PORTB ;全消灯
(実はこれは間違っています)
この次に通常の点灯処理を続けますが、パターン2は順次BITC番目
のビットを点灯したままにして行けば良いので下記となります。
PTN2LPは飛び先用のラベルです。
PTN2LP
BCF PORTB,BITC ;BITC番目のビットを0にセット
(実はこれは間違っています)
この後は、BITCを+1して、1秒間の待ちを挿入して戻ります。
INCF BITC,F ;BITCの内容を+1する
CALL T1SEC
RETURN
以上で各パターンの処理は出来あがりです。
ここでは、各演算命令の実行後反映される、STATUSの各フラグの
条件について確認しておきます。
命令の実行結果のフラグ
命令の実行結果でSTATUSレジスタに影響を与えるものと与えない
ものがある。
これによりその後の条件判定などにSTATUSレジスタの各フラグを
利用する際、注意が必要である。
このSTATUSレジスタのフラグの種類と内容は下記です。
C:Carry Flag
命令実行結果がオーバーフローしたとき1となります。
また減算結果が正の時1となります。
Z:Zero Flag
命令実行結果が0のとき1となります。
DC:Digit Carry Flag
加減算命令実行結果でWregの下位4ビットがオーバーフロー
したとき1となります。また演算結果は正の時も1となります。
良く間違うもの
(1)SUBWFは結果が正の時 C=1となる
Z80系のマイコンは負の時C=1になるので逆になっているので注意
またSUBWF命令も F-Wreg という引き算でやはり逆なので注意。
(2)INCF、DECFのカウントアップダウン命令はZフラグにのみ影響し、
Cフラグには影響しないので注意。
(3)RLF、RRFのロテート命令はCフラグも含めてロテートするので注意。
Cフラグをあらかじめクリアしておかないとロテートで値が変わる。