一、实操考题

主题:按键计数器

器件:ESP32主控板、四位数码管、按键模块、74HC595移位寄存器芯片(或模块)及相关器件。

要求

使用74HC595移位寄存器芯片控制四位数码管显示按键的次数。

具体要求如下:

1、程序启动后,四位数码管显示今天的日期:0326。

2、1次按下并释放按键,四位数码管清空当前数据,显示0。

3、2次按下并释放按键,四位数码管显示1。

4、3次按下并释放按键,四位数码管显示2。

5、再次按下并释放按键,四位数码管显示的数字为先前显示的数字加1,依此类推。

6、程序采用C代码编写,不得使用外部库调用。

7、未作规定处可自行处理,无明显与事实违背即可。

8、编写程序文件命名规则为:DJKS5_身份证号,考试完毕拷贝上交备案。

9、程序编写过程中不得打开库例程和其它程序,如发现,实操成绩按照0分处理。

 

说明:

1、数组NUM[] 保存的是0~9和'.'十六进制形式的数码管显示的段位信息。编程时可参考使用。

// 保存0~9'.'

byte NUM[] = {0xFC, 0x60, 0xDA, 0xF2, 0x66, 0xB6, 0xBE, 0xE0, 0xFE, 0xF6};

 

二、评分组成

实操题总分100分,由两部分组成,分别为:电路搭设功能呈现。其中电路搭设分值20分,功能呈现80分。

三、电路搭设评分 -- 总分20分

原器件:

1、装置中包含74HC595移位寄存器模块(或元器件),得4分。

2、装置中包含四位数码管,得 2分。

3、装置中包含按键模块,得2分

电路搭设:

4、四位数码管与74HC595连接正确连接,得4分。

5、74HC595与主控板正确连接,得4分。

6、按键模块与主控板正确连接,得4分。

四、功能呈现评分 -- 总分80分

1、程序启动后,四位数码管显示今天的日期数字“0326”,15分。

2、1次按下并释放按键,四位数码管清空当前数据,并显示0,15分。

3、2次按下并释放按键,四位数码管显示1,10分。

4、3次按下并释放按键,四位数码管显示2,10分。

5、测评老师要求考生连续按键,当考生第11次按下并释放按键,四位数码管显示10,10分。

6、当考生按下按键时,测评老师要求考生按键保持按下一段时间,在此期间,四位数码管显示的数字没有出现乱码或黑屏,得20分。

 

代码如下:

//主题:按键计数器

//器件:ESP32主控板、四位数码管、按键模块、74HC595移位寄存器芯片(或模块)及相关器件。

//要求:

//使用74HC595移位寄存器芯片控制四位数码管显示按键的次数。

//具体要求如下:

//1、程序启动后,四位数码管显示今天的日期:0326。

//2、第1次按下并释放按键,四位数码管清空当前数据,显示0。

//3、第2次按下并释放按键,四位数码管显示1。

//4、第3次按下并释放按键,四位数码管显示2。

//5、再次按下并释放按键,四位数码管显示的数字为先前显示的数字加1,依此类推。

//6、程序采用C代码编写,不得使用外部库调用。

 

 

const int datapin = 23;         //DS

const int clockpin = 18;        //SH_CP

const int latchpin = 5;         //ST_CP

 

const int keypin = 36;         //按键

int preKeyVal = 1;             //保持先前按键值

int preKeyState = 1;           //保持按键状态值

boolean KeyFlag = false;       //按键状态变量

unsigned int preTime = 0;      //保存millis()返回值

int debounceDelay = 10;        //设定消抖时间间隔

 

unsigned char showStatus = 0;  //0:显示0326,1:显示计数的内容。

unsigned int keyCount = -1;

 

const byte NUM[] = {0xFC,0x60,0xDA,0xF2,0x66,0xB6,0xBE,0xE0,0xFE,0xF6,0x01,0x00};    //0~9 . (空显示,NUM[11] )

int digit = 2;           //在4位数码管第二位显示

int number = 3;          //显示的具体数字'2',number值为10时,显示‘.';

void specialDigitDisplay(int digit,int number)

{

  byte val = 0;

  val = bitSet(val,digit - 1);       //将digit对应位号置位  

  shiftOut(datapin,clockpin,MSBFIRST,val);  //串行移位函数

  shiftOut(datapin,clockpin,LSBFIRST,~NUM[number]);

  digitalWrite(latchpin,HIGH);           //更新数据

  digitalWrite(latchpin,LOW);  

}

 

void getKeyState(void)

{

  int keyVal = digitalRead(keypin) ;    //读取按键值

  if(keyVal!=preKeyVal)

  {

    preTime = millis();                 //获取当前时间

    preKeyVal = keyVal;                 //将当前值赋值给先前值

  } 

  if((millis() - preTime)>debounceDelay)  //判断时间间隔是否大于设定的消抖时间,再判断按键状态是否发生变化

  {

    if(keyVal!=preKeyState)               //是否松手

    {

      preKeyState = keyVal;

      if(keyVal==HIGH)

      {

        //KeyFlag = !KeyFlag;  

        Serial.println("keydown");

        showStatus = 1;      //按下之后,开始显示计数的内容

        keyCount++;          //从-1开始计数

      }  

    } 

  }

}

 

 

void setup() {

  // put your setup code here, to run once:

  pinMode(datapin,OUTPUT);

  pinMode(clockpin,OUTPUT);

  pinMode(latchpin,OUTPUT);         //配置为输出模式

  digitalWrite(clockpin,LOW);       //设置为低电平状态

  digitalWrite(latchpin,LOW);       //设置为低电平状态

  Serial.begin(9600);

  pinMode(keypin,INPUT);            //设置按键为输入状态

}

void showNumCount(int value)

{

  if(value>=1000)    //显示四位数字

  {

    specialDigitDisplay(1,value/1000);      //在第1位显示数字

    specialDigitDisplay(2,value%1000/100);  //在第2位显示数字

    specialDigitDisplay(3,value%100/10);    //在第3位显示数字

    specialDigitDisplay(4,value%10/1);      //在第4位显示数字

  }

  else if(value>=100) //显示三位数字

  {

    specialDigitDisplay(1,11);               //在第1位显示数字,显示为空

    specialDigitDisplay(2,value%1000/100);  //在第2位显示数字

    specialDigitDisplay(3,value%100/10);    //在第3位显示数字

    specialDigitDisplay(4,value%10/1);      //在第4位显示数字

  }

  else if(value>=10) //显示二位数字

  {

    specialDigitDisplay(1,11);               //在第1位显示数字,显示为空

    specialDigitDisplay(2,11);               //在第2位显示数字.显示为空

    specialDigitDisplay(3,value%100/10);    //在第3位显示数字

    specialDigitDisplay(4,value%10/1);      //在第4位显示数字

  }

  else   // if(value>=0) //显示一位数字

  {

    specialDigitDisplay(1,11);               //在第1位显示数字,显示为空

    specialDigitDisplay(2,11);               //在第2位显示数字.显示为空

    specialDigitDisplay(3,11);               //在第3位显示数字.显示为空

    specialDigitDisplay(4,value%10/1);      //在第4位显示数字

  }

}

 

void loop() {

  // put your main code here, to run repeatedly:

  if(showStatus==0)

  {

    specialDigitDisplay(1,0);  //在第1位显示数字4

    specialDigitDisplay(2,3);  //在第2位显示数字5

    specialDigitDisplay(3,2);  //在第3位显示数字6

    specialDigitDisplay(4,6);  //在第4位显示数字7

  }

  else

  {

      showNumCount(keyCount);

  }

  getKeyState();          //获取按键信息

}