Code: Select all
#define DATA_COMMAND 0X40
#define DISP_COMMAND 0x80
#define ADDR_COMMAND 0XC0
//TM1638模块引脚定义
#define DIO_GPIO 23
#define DIO_ON digitalWrite(DIO_GPIO, HIGH)
#define DIO_OFF digitalWrite(DIO_GPIO, LOW)
#define DIO_VAL digitalRead(DIO_GPIO)
#define DIO_IN pinMode(DIO_GPIO, INPUT_PULLUP)
#define DIO_OUT pinMode(DIO_GPIO, OUTPUT)
#define CLK_GPIO 22
#define CLK_ON digitalWrite(CLK_GPIO, HIGH)
#define CLK_OFF digitalWrite(CLK_GPIO, LOW)
#define STB_GPIO 21
#define STB_ON digitalWrite(STB_GPIO, HIGH)
#define STB_OFF digitalWrite(STB_GPIO, LOW)
//共阴数码管显示代码
uint8_t tab[]={0x3F,0x06,0x5B,0x4F,0x66,0x6D,0x7D,0x07,
0x7F,0x6F,0x77,0x7C,0x39,0x5E,0x79,0x71,0x00};
#define LED_BUILTIN 2
bool high_low = true;
uint8_t cnt1S = 0;
uint8_t keyCnt = 0;
uint8_t keyVal = 0;
uint8_t keyNow = 0;
uint8_t num[8]={0,0,0,0,0,0,0,0};
uint8_t batterylevel = 99;
int32_t elevation = 0; // BLE Characteristic uses sint24_t
void TM1638_Write(uint8_t data) //写数据函数
{
uint8_t i;
for(i=0;i<8;i++)
{
CLK_OFF;
asm("NOP");
if (data & 0X01)
DIO_ON;
else
DIO_OFF;
data >>= 1;
CLK_ON;
asm("NOP");
}
}
uint8_t TM1638_Read(void) //读数据函数
{
uint8_t i;
uint8_t temp=0;
DIO_IN; //设置为输入
for(i=0;i<8;i++)
{
temp>>=1;
CLK_OFF;
asm("NOP");
CLK_ON;
asm("NOP");
if(DIO_VAL==HIGH)
temp|=0x80;
}
DIO_OUT; //设置为输出
return temp;
}
void Write_COM(uint8_t cmd) //发送命令字
{
STB_OFF;
TM1638_Write(cmd);
STB_ON;
}
uint8_t Read_key(void)
{
uint8_t c[4],i,key_value;
STB_OFF;
TM1638_Write(0x42); //读键扫数据 命令
for (i=0;i<4;i++) {
c[i]=TM1638_Read();
}
STB_ON; //4个字节数据合成一个字节
key_value=0;
for (i=0;i<4;i++) {
if (c[i] &0x01) key_value |= (0x01<<(i));
if (c[i] &0x10) key_value |= (0x01<<(i+4));
}
if (key_value>0) Serial.printf("Key=%02x\n", key_value);
for(i=0;i<8;i++) {
if((0x01<<i) & key_value)
break;
}
return i;
}
void Write_DATA(uint8_t add,uint8_t data) //指定地址写入数据
{
Write_COM(0x44);
STB_OFF;
TM1638_Write(0xc0|add);
TM1638_Write(data);
STB_ON;
}
/*
void Write_oneLED(uint8_t num,uint8_t flag) //单独控制一个LED函数,num为需要控制的led序号,flag为0时熄灭,不为0时点亮
{
if(flag)
Write_DATA(2*num+1,1);
else
Write_DATA(2*num+1,0);
} */
void Write_allLED(uint8_t LED_flag) //控制全部LED函数,LED_flag表示各个LED状态
{
uint8_t i;
for(i=0;i<8;i++)
{
if(LED_flag&(1<<i))
//Write_DATA(2*i+1,3);
Write_DATA(2*i+1,1);
else
Write_DATA(2*i+1,0);
}
}
//TM1638初始化函数
void init_TM1638(void)
{
uint8_t i;
pinMode(DIO_GPIO, OUTPUT);
pinMode(CLK_GPIO, OUTPUT);
pinMode(STB_GPIO, OUTPUT);
Write_COM(0x8b); //亮度 (0x88-0x8f)8级亮度可调
Write_COM(0x40); //采用地址自动加1
STB_OFF; //
TM1638_Write(0xc0); //设置起始地址
for(i=0;i<16;i++) //传送16个字节的数据
TM1638_Write(0x00);
STB_ON;
for(i=0;i<8;i++)
if (i<2 ||i>5)
Write_DATA(i<<1,tab[0]); //初始化寄存器
else
Write_DATA(i<<1,tab[16]); //初始化寄存器
}
// Setup
void setup() {
// initialize digital pin LED_BUILTIN as an output.
pinMode(LED_BUILTIN, OUTPUT);
init_TM1638();
Write_DATA(0,tab[batterylevel/10]);
Write_DATA(2,tab[batterylevel%10]);
Serial.begin(115200);
} // Setup
// Main
void loop() {
keyNow = Read_key();
if(keyVal != keyNow)
{
if (keyCnt>=3) {
Serial.printf("Key=%02x, Cnt=%d\n", keyVal,keyCnt);
keyCnt=0;
if (keyVal<8) {
num[keyVal]++;
if(num[keyVal]>15)
num[keyVal]=0;
if (keyVal==0 && batterylevel<95) batterylevel +=5;
if (keyVal==1 && batterylevel>5) batterylevel -=5;
Write_DATA(0,tab[batterylevel/10]);
Write_DATA(2,tab[batterylevel%10]);
//Write_DATA(keyVal*2,tab[num[keyVal]]);
}
}
keyVal=keyNow;
keyCnt=0;
}
else {
keyCnt++;
}
if (keyVal<8) Write_allLED(1<<keyVal);
else Write_allLED(0);
delay(20);
} // Main