本次实验学习使用CH549上ADC模块的触摸按键功能,利用CH549EVT学习开发板上与P00、P01、P02、P03连接的四个触摸按键K1、K2、K3、K4分别控制与P22、P23、P24、P25连接的四个LED亮、灭。
一、实验资源
1、CH549EVT学习开发板;
2、Keil v5.28.0.0;
3、CH549开发资料汇总.rar;
4、WCHISPTool v2.70;
5、CH549EVT其它相关文档;
6、沁恒USB转串口模块;
7、串口调试助手SSCOM51 v5.13.1;
二、实验准备
1、CH549触摸按键。TouchKey被设置在了与ADC功能共用的端口,CH549共有16个12位ADC端口,分布在P0[7:0]与P2[7:0],支持16个外部触摸按键。触摸按键的检测利用了电容充放电,并通过ADC模块进行采集、判断。
TouchKey相关的寄存器还有一个“TKEY_CTRL ”,在这个寄存器中存储着触摸按键充电脉冲宽度数据,由于只有低7位有效,故其数据范围为“0~127”。这一数值的确定与触摸按键的外部电容值、微控制器的工作电压以及工作时钟频率相关。在具体的应用中应该考虑。计算公式如下:
count=(Ckey+Cint)*0.7VDD/ITKEY/(2/Fsys)=(25p+15p)*0.35*5*12M/50u=17
TKEY_CTRL=count > 127 ? 127 : count
对于触摸按键的具体使用步骤手册中也给出了详细的说明:
三、本次实验
实验中同时使用了串口(UART0),用于观察按键的工作状态。由于前面的试验已经调试过UART0,这次实验直接包含相关的文件就可以了。CH549EVT上的四个触摸按键K1、K2、K3、K4分别连接到P00、P01、P02、P03,这四个GPIO端口对应着触摸按键输入通道的AIN8、AIN9、AIN10、AIN11。功能实现的程序代码是在官方例程的基础上删减、修改而成。
测试代码如下:
void TouchKey_Init( void )//触摸按键初始化
{
//Touch采样通道设置为高阻输入
P0_MOD_OC &= 0xF0; //P00 P01 P02 P03高阻输入
P0_DIR_PU &= 0xF0;
ADC_CFG |= (bADC_EN|bADC_AIN_EN); //开启ADC模块电源,选择外部通道
ADC_CFG = ADC_CFG & ~(bADC_CLK0 | bADC_CLK1); //选择ADC参考时钟750KHz
ADC_CHAN = (3<<4); //默认选择外部通道0
ADC_CTRL = bADC_IF; //清除ADC转换完成标志,写1清零
IE_ADC = 1; //开启ADC中断使能
EA = 1; //开启总中断使能
}
UINT16 TouchKeySelect(UINT8 ch,UINT8 cpw)//触摸按键通道选择
{
ADC_CHAN = ADC_CHAN & (~MASK_ADC_CHAN) | ch; //外部通道选择
GetValueFlag = 0; //标志位清0
TKEY_CTRL = cpw; //充电脉冲宽度配置,仅低7位有效(同时清除bADC_IF,启动一次TouchKey)
while(GetValueFlag == 0); //等待采用完成
while(ADC_CTRL & bTKEY_ACT);//bTKEY_ACT=1时,表示正在给电容充电和ADC测量过程中
return (ADC_DAT & 0x0FFF);
}
void ADC_ISR(void) interrupt INT_NO_ADC///触摸按键数据采集中断
{
if(ADC_CTRL & bADC_IF)
{
ADC_CTRL = bADC_IF; //清除ADC转换完成标志
GetValueFlag = 1; //采样完成标志
}
}
int main(void)
{
UINT8 ch;
UINT16 value;
UINT16 err;
SAFE_MOD = 0x55;
SAFE_MOD = 0xAA; //进入安全模式
CLOCK_CFG = 0X85; //使能内部晶振,Fsys=24MHz
CLK_Config();
UART0_Config();
printf("TouchKey test\n");
LED_Port_Init();
TouchKey_Init();
Press_Flag = 0; //无按键按下
/* 获取按键初值 */
for(ch = 8; ch!=12; ch++)
{
PowerValue[ch] = TouchKeySelect(ch,CPW_Table[ch]);
printf("%d ",PowerValue[ch] );
}
printf("\n");
while(1)
{
/* 按键检测 */
for(ch = 8; ch!=12; ch++)
{
value = TouchKeySelect(ch,CPW_Table[ch]);
err = ABS(PowerValue[ch],value);
if(err > DOWM_THRESHOLD_VALUE) //差值大于阈值,认为按下
{
if((Press_Flag & (1<<ch)) == 0) //说明是第一次按下
{
printf("ch %d pressed,value:%d\n",(UINT16)ch, value);
/* 点灯处理 */
LED_Control(ch-8,1);
}
Press_Flag |= (1<<ch);
}
else if(err < UP_THRESHOLD_VALUE) //说明抬起或者未按下
{
if(Press_Flag & (1<<ch)) //刚抬起
{
Press_Flag &= ~(1<<ch);
printf("ch %d up,value:%d\n",(UINT16)ch, value);
/* 灭灯处理 */
LED_Control(ch-8,0);
}
}
}
}
}
四、实验结果
实现了基本功能。
五、实验总结
通过本次实验对CH549触摸按键有了初步的认识和了解。因为是第一次使用触摸按键,对于一些知识点的学习不够深入,理解上还存在错误。实验中尝试在板载四位按键表面覆盖一片PVC卡片,就是信用卡那种,厚度不足1mm,但没有成功。也尝试把“CPW_Table[16]”中的数据进行更改,还是没有成功。
此内容由EEWORLD论坛网友lising原创,如需转载或用于商业用途需征得作者同意并注明出处
|