Matrix keyboard should be a kind of device that can be used frequently ,4X4 The matrix keyboard only needs to be used 8 individual IO mouth , That's it 16 Read bit key . Its essential principle is row and column scanning . This article will take you to learn the principle of matrix keyboard and code .

<> The essence of matrix keyboard :

The essence of matrix keyboard is to use 8 individual io I'll do it by mouth 16 Control reading of two buttons , Can be reduced io Use of mouth , use 4 strip I/O Line as line ,4 strip I/O A keyboard consisting of lines as column lines . At each intersection of row and column lines , Set a key . And the number of such keys is 4
X 4 individual .

This determinant keyboard structure can effectively improve the performance of MCU system I/O Utilization rate of water supply . Saving resources of single chip microcomputer , Its essence is similar to the independent button , It's a row by row scan and a column by column scan , And then determine the row and column of the key , And then the overall key value is determined , We use the matrix keyboard is connected to the MCU P1 The port is read through P1 The numerical value reading of matrix keyboard can be completed by level conversion of interface , The specific schematic diagram is as follows :

The first line got it p17, The second line got it p16, The third line received p15, The first 4 Yes, I have p14
The first train receives p13, The second column receives p12, The third column receives p11, The fourth column receives p10

There are two ways to scan matrix keyboard : 1. Line scan ,2. Line by line / Scan column by column

Among them, row and column scanning is suitable for 8 individual IO The interface is connected to the MCU 8 A continuous IO mouth , You can scan the rows and columns

Line by line / Scan column by column Suitable for matrix keyboards connected to arbitrary IO mouth , Line by line , Scan column by column

Next, we will introduce these two methods :

<> Line scan :

principle :

First from P1 The top four of the mouth ( Four lines ) High level output , Four lower ( Four columns ) Output low level , Suppose there's a button down , from P1 The high four bits of the port read the keyboard status . Determine which of the four rows of the upper four bits becomes the low level , You know what line it is , Again from P1 The lower four of the mouth ( Four columns ) Output high level , Senior four ( Four lines ) Output low level , from P1 The lower four bits of the port read the keyboard status . Determine which row of the four columns of the lower four bits becomes the low level , You know what column it is , The feature code of the current key can be obtained by combining the two reading results . Using the above method, we get 16 Feature coding of keys .

Red high , Blue low

Detailed explanation :

According to the schematic diagram of matrix keyboard , If the matrix keyboard 8 individual IO Mouth connected to a continuous one person P10-P17 upper , When no key is pressed , take P1 Oral P1^0 and P13 Set high level P14
and P17 Set low level , That is to say, will 4 It's all right IO Mouth set high ,4 Number of columns IO Lower the mouth . that is P1=0x0f(0000 1111);

If a button is pressed at this time, then P1^0 and P13 One will go low . therefore P1 The value of is not equal to 0x0f, The line where the key is pressed will become low , This is to determine whether a key has been pressed .

Will correspond to P1 Value sum of mouth 0x0f(00001111) mutually And & Then you can get the fourth place in the high school. Which line becomes 0

Bitwise “ And ”&( binary operator ): Only if both operands are 1 Time , The results are as follows 1, Otherwise 0.
For example : 0&0=0;0&1=0;1&0=0;1&1=1
Namely : Both are 1, The results are as follows 1, Otherwise 0

For example, press the first row, the first column 1x1
example :
0000 1110------------- Press 1x1 after P1 Value of
& 0000 1111------------- 0x0f
----------
0000 1110------------- The final result is obtained , First act 0

Give it again P1 Mouth assignment 0X0f. take P1 Oral P1^0 and P13 Set low level P14 and P17 Set high level
, That is to say, will 4 It's a low one IO Mouth set high ,4 Of columns IO Set the port high and read the low four bit level , At this time P1 mouth (1111 0000)

Read the P1 mouth and 0xf0(11110000) mutually And & Then you can get the lower four bits, which column becomes the low level

For example, what we press is 1x1 Key , That's the first row, the first column , At this time, you can see after pressing p1.0 and p1.3 It's all low , take Row=P1&0x0f;( The value of the row ) and
Col=P1&0xf0;// Column value Add , You can get the key you pressed

1x1: ( Line by line )
Row=P1&0x0f =  0000 1110

Col=P1&0xf0=     1110 0000
Row+Col=           1110 1110   = 0xee

Low level 0 Indicates the corresponding row and column

You can see below p1.0 and p1.4 It's low

2x2: ( Two rows and two columns )
Row=P1&0x0f =  0000 1101

Col=P1&0xf0=     1101 0000
Row+Col=           1101 1101   = 0xdd

3x4: ( Three rows and four columns )
Row=P1&0x0f =  0000 1011

Col=P1&0xf0=     0111 0000
Row+Col=           0111 1011   = 0x7b

So you can get all the information 16 Number of buttons , The specific code is as follows :
unsigned char keyscan(){ unsigned char key,Row,Col; P1=0x0f; if(P1!=0x0f){
delay(10);// To shake if(P1!=0x0f){ Row=P1&0x0f;// Make sure the port value is correct ( The value of the row ) P1=0xf0; Col=P1&0xf0;
// Column value } while((P1&0xf0)!=0xf0);// Judge whether the key is raised } switch(Row+Col){ case 0xee:key=0;break
; case 0xde:key=1;break; case 0xbe:key=2;break; case 0x7e:key=3;break; case 0xed
:key=4;break; case 0xdd:key=5;break; case 0xbd:key=6;break; case 0x7d:key=7;
break; case 0xeb:key=8;break; case 0xdb:key=9;break; case 0xbb:key=10;break;
case 0x7b:key=11;break; case 0xe7:key=12;break; case 0xd7:key=13;break; case
0xb7:key=14;break; case 0x77:key=15;break; } return key; }
Operation effect picture :

<> Line by line / Column scan :

Line by line , The essence of column scan is similar to column scan , The essence is to give a certain line / A column , Low level , The other seven are all high level , At this time, read the level conversion , A low level indicates that the key is pressed , You can read the key data .

For example, scan line by line :

* Place in the second place 1 Behavior low level , rest N-1 Xinghe N Listed as high ,
* Read column line data , A low level in the column line indicates that a key is pressed in this line , For example, what you press is 1 Three rows and three columns (1x3), So the line of the third column IO Port is low level .
* Place in the second place 2 Behavior low level , rest N-1 Xinghe N Listed as high ,, Read column line data , A low level in the column line indicates that a key is pressed in this line .
* and so on , Scan line by line .
* According to the different level of the line, we can identify whether the key is pressed , Which button is pressed , Get key number .(N) Jump to the corresponding key processing program according to the key number .
Use our P1 Let me give you an example :

first , to P1 assignment P1=0xfe(1111
1110);, At this time P1.0 Low level ,P1.1~p1.7 High level , If a button is pressed at this time, then the four column lines ,P1.4,P1.5,P1.6,P1.7 One column will go low . therefore P1 The value of is not equal to 0xfe, This is to determine whether a key has been pressed .

Then delay for a period of time to jitter , Then give it to me P1 assignment 0xfd(1111
1101), that is P1.1 Low level , Others are high level , At this time, if there is a P1.1 Online P1.4,P1.5,P1.6,P1.7 There is a key press , Then there will be a low level , So as to determine which button is pressed ; If not, give it to me P1 assignment 0xfb(1111
1011), that is P1.2 Low level , Others are high level . Use the same method to judge whether a key is pressed ;······ And so on , Four tests .

For example, when the first 1 When the key is pressed P1 The corresponding value of is :

  1X1(11101110=0xee)
  1x2(11011110=0xde)
  1X3(10111110=0xbe)
  1X4(01111110=0x7e)
The first 2 When the key is pressed P1 The corresponding value of is :

     2X1(11101101=0xed)
     2x2(11011101=0xdd)
     2X3(10111101=0xbd)
     2X4(01111101=0x7d)

take P1^2 Output low level , Other pins output high level , Namely P1=0xfb, So when the first 3 When the key is pressed P1 The corresponding value of is :
     3X1(11101011=0xeb)
     3x2(11011011=0xdb)
     3X3(10111011=0xbb)
     3X4(01111011=0x7b)

Finally, the corresponding value of the fourth line is :
     4X1(11100111=0xe7)
     4x2(11010111=0xd7)
     4X3(10110111=0xb7)
   4X4(01110111=0x77)

So in the end, we can get the code :
/*****************************************************************************
** Function name :keyscan ** Function description : Key to get function
******************************************************************************/
void keyscan(void) { P1=0xfe; temp=P1; temp=temp&0xf0; if(temp!=0xf0) { delay(10
); if(temp!=0xf0) { temp=P1; switch(temp) { case 0xee: key=0;break; case 0xde:
key=1;break; case 0xbe: key=2;break; case 0x7e: key=3;break; } while(temp!=0xf0)
{ temp=P1; temp=temp&0xf0; } } } P1=0xfd; temp=P1; temp=temp&0xf0; if(temp!=0xf0
) { delay(10); if(temp!=0xf0) { temp=P1; switch(temp) { case 0xed: key=4;break;
case 0xdd: key=5;break; case 0xbd: key=6;break; case 0x7d: key=7;break; } while(
temp!=0xf0) { temp=P1; temp=temp&0xf0; } } } P1=0xfb; temp=P1; temp=temp&0xf0;
if(temp!=0xf0) { delay(10); if(temp!=0xf0) { temp=P1; switch(temp) { case 0xeb:
key=8;break; case 0xdb: key=9;break; case 0xbb: key=10;break; case 0x7b: key=11;
break; } beep=0;delay(50);beep=1; while(temp!=0xf0) { temp=P1; temp=temp&0xf0; }
} } P1=0xf7; temp=P1; temp=temp&0xf0; if(temp!=0xf0) { delay(10); if(temp!=0xf0)
{ temp=P1; switch(temp) { case 0xe7: key=12;break; case 0xd7: key=13;break; case
0xb7: key=14;break; case 0x77: key=15;break; } while(temp!=0xf0) { temp=P1; temp
=temp&0xf0; } } } }
Operation effect picture :

Technology