【LanqiaoCup組み込み拡張ボード】ADCボタンの詳細説明(プログラムソースコード付き)

早い段階で知識を習得する必要があります:

  1. ADCの取得
  2. いくつかの簡単な回路知識

1.実験手順

実験前に[A5-> AKEY]に接続しましたが、
ここでもデジタルチューブを使用したので、** [A1-> SER] [A2-> RCK] [A3-> SCK] **
デジタルチューブを接続しました。これ以上の説明はありません、前の記事を参照してください

https://blog.csdn.net/qq_45689790/article/details/114106264

ここに画像の説明を挿入

2、ハードウェアの概略図

ここに画像の説明を挿入

3.手順

1.ADC関連

static void ADCx_GPIO_Config(void)
{
    
    
	GPIO_InitTypeDef GPIO_InitStruct;
	RCC_APB2PeriphClockCmd(ADC_GPIO_CLK,ENABLE);
	
	GPIO_InitStruct.GPIO_Mode = GPIO_Mode_AIN;
	GPIO_InitStruct.GPIO_Pin = ADC_GPIO_PIN;
	GPIO_Init(ADC_GPIO_PORT,&GPIO_InitStruct); 
}

static void ADCx_Config(void)
{
    
    
	ADC_InitTypeDef ADC_InitStruct;
	
	RCC_APB2PeriphClockCmd(ADC_CLK,ENABLE);
	
	ADC_InitStruct.ADC_ContinuousConvMode = ENABLE;
	ADC_InitStruct.ADC_DataAlign = ADC_DataAlign_Right;
	ADC_InitStruct.ADC_ExternalTrigConv = ADC_ExternalTrigConv_None;
	ADC_InitStruct.ADC_Mode = ADC_Mode_Independent;
	ADC_InitStruct.ADC_NbrOfChannel = 1;
	ADC_InitStruct.ADC_ScanConvMode = DISABLE;
	ADC_Init(ADC_x,&ADC_InitStruct);
	
	//配置ADC时钟为PCLK2的8分频,即9MHz
	RCC_ADCCLKConfig(RCC_PCLK2_Div8); 
	
	ADC_RegularChannelConfig(ADC_x,ADC_Channelx,1,ADC_SampleTime_13Cycles5);
	
	ADC_Cmd(ADC_x,ENABLE);
	
	//初始化ADC 校准寄存器  
	ADC_ResetCalibration(ADC_x);
	//等待校准寄存器初始化完成
	while(ADC_GetResetCalibrationStatus(ADC_x));
	//ADC开始校准
	ADC_StartCalibration(ADC_x);
	//等待校准完成
	while(ADC_GetCalibrationStatus(ADC_x));
	ADC_SoftwareStartConvCmd(ADC_x,ENABLE);  //如果使能连续转换,那么直接软件触发一次转换即可
}

void ADCx_Init(void)
{
    
    
	ADCx_GPIO_Config();
	ADCx_Config();
}

uint16_t ADC_Read(void)
{
    
    
	uint16_t ADC_Value = 0;
	//ADC_SoftwareStartConvCmd(ADC_x,ENABLE);
	while(ADC_GetFlagStatus(ADC_x, ADC_FLAG_EOC) == RESET);
	ADC_Value = ADC_GetConversionValue(ADC_x);
	ADC_ClearFlag(ADC_x, ADC_FLAG_EOC);

	return ADC_Value;
}
}

「bsp_adc.h」

#ifndef _BSP_ADC_H
#define _BSP_ADC_H
#include "stm32f10x.h"

#define ADC_GPIO_PORT		GPIOA
#define ADC_GPIO_PIN		GPIO_Pin_5
#define ADC_GPIO_CLK		RCC_APB2Periph_GPIOA

#define ADC_x						ADC1
#define ADC_CLK					RCC_APB2Periph_ADC1
#define ADC_Channelx		ADC_Channel_5

void ADCx_Init(void);
uint16_t ADC_Read(void);
#endif /*_BSP_ADC_H*/

2.ボタン関連

static uint16_t btn_buff[BTN_BUFF_LEN];
//
uint16_t Read_Btn(void)
{
    
    
	//滤波函数
	u16 tmp = 0;
	u8 i = 0,j = 0;
	for(i=0; i<BTN_BUFF_LEN; i++){
    
    
		btn_buff[i] = ADC_Read();
	}
	
	for(i=0; i<BTN_BUFF_LEN; i++)//冒泡排序
	{
    
    
		for(j=0; j<	BTN_BUFF_LEN-i; j++)
		{
    
    
			if(btn_buff[j+1] < btn_buff[j]) //大的放后边
			{
    
    
				tmp = btn_buff[j+1];
				btn_buff[j+1] = btn_buff[j];
				btn_buff[j] = tmp;
			}
		}
	}
	if(BTN_BUFF_LEN % 2 == 0)
	{
    
    
		return(btn_buff[BTN_BUFF_LEN/2-1] + btn_buff[BTN_BUFF_LEN/2])/2;
	}else
	{
    
    
		return(btn_buff[BTN_BUFF_LEN/2]);
	}
}

uint8_t Scan_Btn(void)
{
    
    
	u16 btn_tmp = 0;

	btn_tmp = Read_Btn();
	if(btn_tmp < 0x0FFF/14){
    
    
		return 1;
	}else if((btn_tmp > 0x0FFF/14) && (btn_tmp < 0x0FFF/14*3)){
    
    
		return 2;
	}else if((btn_tmp > 0x0FFF/14*3) && (btn_tmp < 0x0FFF/14*5)){
    
    
		return 3;
	}else if((btn_tmp > 0x0FFF/14*5) && (btn_tmp < 0x0FFF/14*7)){
    
    
		return 4;
	}else if((btn_tmp > 0x0FFF/14*7) && (btn_tmp < 0x0FFF/14*9)){
    
    
		return 5;
	}else if((btn_tmp > 0x0FFF/14*9) && (btn_tmp<0x0C00)){
    
    //(btn_tmp < 0x0FFF/14*11))
		return 6;
	}else if((btn_tmp > 0x0C00) && (btn_tmp < 0X0D00)){
    
    
		return 7;
	}else if((btn_tmp > 0X0D00)&& (btn_tmp < 0x0FDF)) {
    
     //
		return 8;
	}
	else{
    
    
		return 0;	//error status & no key
	}
}

「bsp_button.h」

#ifndef _BSP_BUTTON_H
#define _BSP_BUTTON_H
#include "stm32f10x.h"
#define BTN_BUFF_LEN	50

uint16_t Read_Btn(void);
uint8_t Scan_Btn(void);
#endif /*_BSP_BUTTON_H*/

"メイン"

#include "stm32f10x.h"
#include "bsp_seg.h"
#include "lcd.h"
#include "bsp_adc.h"
#include "bsp_button.h"
#include <stdio.h>
u32 DelayTiming = 0;

void Delay_Ms(u32 nTime)
{
    
    
	DelayTiming = nTime;

	while(DelayTiming != 0);
}
char txt[20];

uint8_t key_val = 0;
int main(void)
{
    
    
	SysTick_Config(SystemCoreClock/1000);
	
	STM3210B_LCD_Init();
	LCD_Clear(White);
	STM3210B_LCD_Init();
	
	SEG_GPIO_Config();
	ADCx_Init();

	LCD_SetTextColor(White);
	LCD_SetBackColor(Blue);

	LCD_ClearLine(Line0);
	LCD_ClearLine(Line1);
	LCD_ClearLine(Line2);
	LCD_ClearLine(Line3);
	LCD_ClearLine(Line4);
	
	LCD_DisplayStringLine(Line1,(u8*)"    BUTTON DEMO     ");

	LCD_SetTextColor(Blue);
	LCD_SetBackColor(White);
	while(1)
	{
    
    
		sprintf(txt, "Button ADC:%04X", Read_Btn());
		LCD_DisplayStringLine(Line6,(uint8_t*)txt);
		
		key_val = Scan_Btn();
		
		if(key_val != 0)
		{
    
    
			SEG_Display(16, 16, key_val);
			sprintf(txt, "Button Value:%d", key_val);
			LCD_DisplayStringLine(Line7,(uint8_t*)txt);
		}
	}
	
}

おすすめ

転載: blog.csdn.net/qq_45689790/article/details/114115455