デジタルスイッチを使ったプログラムの続きです。
デジタルスイッチの数値(0〜15)をLCD・液晶ディスプレイの画面に表示するプログラムです。回路図を下に示します。PB0〜PB3にデジタルスイッチをつなぎます。LCDはいつものようにPA2〜PA7に接続しました。なお、PB4〜PB6はGNDに落としています。ここをアースしないと動作が不安定になり、変な数字が出ることがありました。あとから思ったのですが、使わない入力端子も含めてすべてプルアップしておけばよいのかもしれません。
プログラムは下記の通りです。マイコンICにプログラムを書き込む際は、デジタルスイッチの数字を「0」にしておいてください。
プログラムファイル digisw2a.bas
1 | $regfile = "at26def.dat" | ATtiny26Lを使用する。 | |
2 | $crystal = 1000000 | クロック周波数を1MHzに設定。 | |
3 | |||
4 | Config Lcdpin=Pin , Db4=Porta.4 , Db5=Porta.5 | LCDの接続設定。DB4=PA4, DB5=PA5。 | |
5 | Config Lcdpin=Pin , Db6=Porta.6 , Db7=Porta.7 | LCDの接続設定。DB6=PA6, DB7=PA7。 | |
6 | Config Lcdpin=Pin , E=Porta.3 , Rs=Porta.2 | LCDの接続設定。E=PA3, RS=PA2。 | |
7 | Config Lcd = 16 * 2 | 16桁x2行表示のLCDを使用する。 | |
8 | Config Portb = Input | ポートBを入力に設定する。 | |
9 | Portb = &B00001111 | PB3〜PB0をプルアップする。 | |
10 | Dim N As Byte | バイト型変数「N」を使用する。 | |
11 | Cursor Off | カーソルを表示しない。 | |
12 | |||
13 | Do | Doループの範囲ここから。 | |
14 | N = Pinb | ポートBの入力を「N」に代入する。 | |
15 | N = 15 - N | 「15−N」を「N」とする。 | |
16 | Cls | LCDの表示を消去する。 | |
17 | Lcd "Input=" ; N | LCDに「Input=」と変数「N」の値を表示する。 | |
18 | Wait 1 | 1秒間そのまま。 | |
19 | Loop | Doループの範囲ここまで。13行目へ戻る。 | |
20 | |||
21 | End | 終わり。 |
デジタルスイッチ | ポートB入力 | Pinb (2進数) | N | 15−N | |||||||
番号 | D | C | B | A | 3 | 2 | 1 | 0 | |||
0 | 0 | 0 | 0 | 0 | 1 | 1 | 1 | 1 | 0000 1111 | 15 | 0 |
1 | 0 | 0 | 0 | 1 | 1 | 1 | 1 | 0 | 0000 1110 | 14 | 1 |
2 | 0 | 0 | 1 | 0 | 1 | 1 | 0 | 1 | 0000 1101 | 13 | 2 |
3 | 0 | 0 | 1 | 1 | 1 | 1 | 0 | 0 | 0000 1100 | 12 | 3 |
(中 略) | |||||||||||
15 | 1 | 1 | 1 | 1 | 0 | 0 | 0 | 0 | 0000 0000 | 0 | 15 |
デジタルスイッチの番号とポート入力、および変数「N」の関係を上の表に示します。スイッチが「0」のときは内部スイッチD〜Aの接点はすべて開いています。この状態ではPB3〜PB0はすべて「1」になります(プルアップしたから)。したがって入力値は2進数の「1111」すなわち「N = 15」です。そこで15行目「N = 15 - N」によって「N」の値を「0」にしています。スイッチの数字が増えるにつれて、入力値は逆に15から1ずつ減っていきます。
デジタルスイッチの数値に応じた個数のLEDが点灯するプログラムを作りました。ポートAに8個のLEDをつなぎます。回路図を下に示します。
LEDの点灯のしかたは下の表のようになります。0から8まではLED0から順に1個ずつ点灯していきます。8ですべてのLEDが点灯します。8を超えるとLED0から順に1個ずつ消灯します。
入力 | LED7 | LED6 | LED5 | LED4 | LED3 | LED2 | LED1 | LED0 |
0 | ||||||||
1 | ||||||||
2 | ||||||||
(中 略) | ||||||||
8 | ||||||||
9 | ||||||||
10 | ||||||||
(中 略) | ||||||||
15 |
プログラムは下記の通りです。変数「N」の値を3通りに分類し、それぞれ条件分岐によって処理します。
プログラムファイル digisw2b.bas
1 | $regfile = "at26def.dat" | ATtiny26Lを使用する。 | |
2 | $crystal = 1000000 | クロック周波数を1MHzに設定。 | |
3 | |||
4 | Config Porta = Output | ポートAを出力に設定する。 | |
5 | Config Portb = Input | ポートBを入力に設定する。 | |
6 | Portb = &B00001111 | PB3〜PB0をプルアップする。 | |
7 | Dim N As Byte | バイト型変数「N」を使用する。 | |
8 | Dim Led As Byte | バイト型変数「Led」を使用する。 | |
9 | |||
10 | Do | Doループの範囲ここから。 | |
11 | Porta = 0 | ポートAの出力を「0」にする。 | |
12 | N = Pinb | ポートBの入力を変数「N」に代入する。 | |
13 | N = 15 - N | 「15−N」を新たな「N」とする。 | |
14 | If N = 0 Then | 条件分岐1。「N=0」ならば、 | |
15 | Porta = 0 | すべてのLEDを消灯する。 | |
16 | End If | 条件分岐1ここまで。 | |
17 | If 0 < N And N < 8 Then | 条件分岐2。「0<N<8」ならば、 | |
18 | N = N - 1 | 「N−1」を新たな「N」とする。 | |
19 | For Led = 0 To N | Forループ。「0」から「N」まで繰り返し。 | |
20 | Porta.led = 1 | LED0から「LED・N」までを点灯する。 | |
21 | Next Led | Forループここまで。 | |
22 | End If | 条件分岐2ここまで。 | |
23 | If 8 <= N Then | 条件分岐3。「8≤N」ならば、 | |
24 | N = N - 8 | 「N−8」を新たな「N」とする。 | |
25 | For Led = N To 7 | Forループ。「N」から「7」まで繰り返し。 | |
26 | Porta.led = 1 | 「LED・N」からLED7までを点灯する。 | |
27 | Next Led | Forループここまで。 | |
28 | End If | 条件分岐3ここまで。 | |
29 | Waitms 100 | 0.1秒間そのまま。 | |
30 | Loop | Doループの範囲ここまで。10行目へ戻る。 | |
31 | |||
32 | End | 終わり。 |
13行目「N = 15 - N」を終えた時点で、変数「N」の値は0〜15までのいずれかになります。「N = 0」のときは15行目「Porta = 0」によってすべてのLEDを消灯します。「0 < N And N < 8」、つまり「N」が0より大きくて8より小さいときは、「N」から1を引き、LED0から「LED・N」までを点灯します。例えば「N = 5」だったらLED0〜LED4が点灯します。「8≤N」のときは「N」から8を引き、「LED・N」からLED7までを点灯します。例えば「N = 10」だったらLED2〜LED7が点灯します。